]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/boost/asio/experimental/detail/channel_send_op.hpp
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / boost / boost / asio / experimental / detail / channel_send_op.hpp
1 //
2 // experimental/detail/channel_send_op.hpp
3 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
4 //
5 // Copyright (c) 2003-2022 Christopher M. Kohlhoff (chris at kohlhoff dot com)
6 //
7 // Distributed under the Boost Software License, Version 1.0. (See accompanying
8 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
9 //
10
11 #ifndef BOOST_ASIO_EXPERIMENTAL_DETAIL_CHANNEL_SEND_OP_HPP
12 #define BOOST_ASIO_EXPERIMENTAL_DETAIL_CHANNEL_SEND_OP_HPP
13
14 #if defined(_MSC_VER) && (_MSC_VER >= 1200)
15 # pragma once
16 #endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
17
18 #include <boost/asio/detail/config.hpp>
19 #include <boost/asio/detail/bind_handler.hpp>
20 #include <boost/asio/detail/handler_alloc_helpers.hpp>
21 #include <boost/asio/error.hpp>
22 #include <boost/asio/experimental/channel_error.hpp>
23 #include <boost/asio/experimental/detail/channel_operation.hpp>
24 #include <boost/asio/experimental/detail/channel_payload.hpp>
25
26 #include <boost/asio/detail/push_options.hpp>
27
28 namespace boost {
29 namespace asio {
30 namespace experimental {
31 namespace detail {
32
33 template <typename Payload>
34 class channel_send : public channel_operation
35 {
36 public:
37 Payload get_payload()
38 {
39 return BOOST_ASIO_MOVE_CAST(Payload)(payload_);
40 }
41
42 void complete()
43 {
44 func_(this, complete_op, 0);
45 }
46
47 void cancel()
48 {
49 func_(this, cancel_op, 0);
50 }
51
52 void close()
53 {
54 func_(this, close_op, 0);
55 }
56
57 protected:
58 channel_send(func_type func, BOOST_ASIO_MOVE_ARG(Payload) payload)
59 : channel_operation(func),
60 payload_(BOOST_ASIO_MOVE_CAST(Payload)(payload))
61 {
62 }
63
64 private:
65 Payload payload_;
66 };
67
68 template <typename Payload, typename Handler, typename IoExecutor>
69 class channel_send_op : public channel_send<Payload>
70 {
71 public:
72 BOOST_ASIO_DEFINE_HANDLER_PTR(channel_send_op);
73
74 channel_send_op(BOOST_ASIO_MOVE_ARG(Payload) payload,
75 Handler& handler, const IoExecutor& io_ex)
76 : channel_send<Payload>(&channel_send_op::do_action,
77 BOOST_ASIO_MOVE_CAST(Payload)(payload)),
78 handler_(BOOST_ASIO_MOVE_CAST(Handler)(handler)),
79 work_(handler_, io_ex)
80 {
81 }
82
83 static void do_action(channel_operation* base,
84 channel_operation::action a, void*)
85 {
86 // Take ownership of the operation object.
87 channel_send_op* o(static_cast<channel_send_op*>(base));
88 ptr p = { boost::asio::detail::addressof(o->handler_), o, o };
89
90 BOOST_ASIO_HANDLER_COMPLETION((*o));
91
92 // Take ownership of the operation's outstanding work.
93 channel_operation::handler_work<Handler, IoExecutor> w(
94 BOOST_ASIO_MOVE_CAST2(channel_operation::handler_work<
95 Handler, IoExecutor>)(o->work_));
96
97 boost::system::error_code ec;
98 switch (a)
99 {
100 case channel_operation::cancel_op:
101 ec = error::channel_cancelled;
102 break;
103 case channel_operation::close_op:
104 ec = error::channel_closed;
105 break;
106 default:
107 break;
108 }
109
110 // Make a copy of the handler so that the memory can be deallocated before
111 // the handler is posted. Even if we're not about to post the handler, a
112 // sub-object of the handler may be the true owner of the memory associated
113 // with the handler. Consequently, a local copy of the handler is required
114 // to ensure that any owning sub-object remains valid until after we have
115 // deallocated the memory here.
116 boost::asio::detail::binder1<Handler, boost::system::error_code>
117 handler(o->handler_, ec);
118 p.h = boost::asio::detail::addressof(handler.handler_);
119 p.reset();
120
121 // Post the completion if required.
122 if (a != channel_operation::destroy_op)
123 {
124 BOOST_ASIO_HANDLER_INVOCATION_BEGIN((handler.arg1_));
125 w.complete(handler, handler.handler_);
126 BOOST_ASIO_HANDLER_INVOCATION_END;
127 }
128 }
129
130 private:
131 Handler handler_;
132 channel_operation::handler_work<Handler, IoExecutor> work_;
133 };
134
135 } // namespace detail
136 } // namespace experimental
137 } // namespace asio
138 } // namespace boost
139
140 #include <boost/asio/detail/pop_options.hpp>
141
142 #endif // BOOST_ASIO_EXPERIMENTAL_DETAIL_CHANNEL_SEND_OP_HPP