fix doc example typo
[boost.git] / boost / asio / impl / write.ipp
blob4434a912f4d51f57c0e10a38d5f968ace00ccf41
1 //
2 // write.ipp
3 // ~~~~~~~~~
4 //
5 // Copyright (c) 2003-2008 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 //
11 #ifndef BOOST_ASIO_WRITE_IPP
12 #define BOOST_ASIO_WRITE_IPP
14 #if defined(_MSC_VER) && (_MSC_VER >= 1200)
15 # pragma once
16 #endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
18 #include <boost/asio/detail/push_options.hpp>
20 #include <boost/asio/buffer.hpp>
21 #include <boost/asio/completion_condition.hpp>
22 #include <boost/asio/detail/bind_handler.hpp>
23 #include <boost/asio/detail/consuming_buffers.hpp>
24 #include <boost/asio/detail/handler_alloc_helpers.hpp>
25 #include <boost/asio/detail/handler_invoke_helpers.hpp>
26 #include <boost/asio/detail/throw_error.hpp>
28 namespace boost {
29 namespace asio {
31 template <typename SyncWriteStream, typename ConstBufferSequence,
32     typename CompletionCondition>
33 std::size_t write(SyncWriteStream& s, const ConstBufferSequence& buffers,
34     CompletionCondition completion_condition, boost::system::error_code& ec)
36   ec = boost::system::error_code();
37   boost::asio::detail::consuming_buffers<
38     const_buffer, ConstBufferSequence> tmp(buffers);
39   std::size_t total_transferred = 0;
40   tmp.set_max_size(detail::adapt_completion_condition_result(
41         completion_condition(ec, total_transferred)));
42   while (tmp.begin() != tmp.end())
43   {
44     std::size_t bytes_transferred = s.write_some(tmp, ec);
45     tmp.consume(bytes_transferred);
46     total_transferred += bytes_transferred;
47     tmp.set_max_size(detail::adapt_completion_condition_result(
48           completion_condition(ec, total_transferred)));
49   }
50   return total_transferred;
53 template <typename SyncWriteStream, typename ConstBufferSequence>
54 inline std::size_t write(SyncWriteStream& s, const ConstBufferSequence& buffers)
56   boost::system::error_code ec;
57   std::size_t bytes_transferred = write(s, buffers, transfer_all(), ec);
58   boost::asio::detail::throw_error(ec);
59   return bytes_transferred;
62 template <typename SyncWriteStream, typename ConstBufferSequence,
63     typename CompletionCondition>
64 inline std::size_t write(SyncWriteStream& s, const ConstBufferSequence& buffers,
65     CompletionCondition completion_condition)
67   boost::system::error_code ec;
68   std::size_t bytes_transferred = write(s, buffers, completion_condition, ec);
69   boost::asio::detail::throw_error(ec);
70   return bytes_transferred;
73 template <typename SyncWriteStream, typename Allocator,
74     typename CompletionCondition>
75 std::size_t write(SyncWriteStream& s,
76     boost::asio::basic_streambuf<Allocator>& b,
77     CompletionCondition completion_condition, boost::system::error_code& ec)
79   std::size_t bytes_transferred = write(s, b.data(), completion_condition, ec);
80   b.consume(bytes_transferred);
81   return bytes_transferred;
84 template <typename SyncWriteStream, typename Allocator>
85 inline std::size_t write(SyncWriteStream& s,
86     boost::asio::basic_streambuf<Allocator>& b)
88   boost::system::error_code ec;
89   std::size_t bytes_transferred = write(s, b, transfer_all(), ec);
90   boost::asio::detail::throw_error(ec);
91   return bytes_transferred;
94 template <typename SyncWriteStream, typename Allocator,
95     typename CompletionCondition>
96 inline std::size_t write(SyncWriteStream& s,
97     boost::asio::basic_streambuf<Allocator>& b,
98     CompletionCondition completion_condition)
100   boost::system::error_code ec;
101   std::size_t bytes_transferred = write(s, b, completion_condition, ec);
102   boost::asio::detail::throw_error(ec);
103   return bytes_transferred;
106 namespace detail
108   template <typename AsyncWriteStream, typename ConstBufferSequence,
109       typename CompletionCondition, typename WriteHandler>
110   class write_handler
111   {
112   public:
113     typedef boost::asio::detail::consuming_buffers<
114       const_buffer, ConstBufferSequence> buffers_type;
116     write_handler(AsyncWriteStream& stream, const buffers_type& buffers,
117         CompletionCondition completion_condition, WriteHandler handler)
118       : stream_(stream),
119         buffers_(buffers),
120         total_transferred_(0),
121         completion_condition_(completion_condition),
122         handler_(handler)
123     {
124     }
126     void operator()(const boost::system::error_code& ec,
127         std::size_t bytes_transferred)
128     {
129       total_transferred_ += bytes_transferred;
130       buffers_.consume(bytes_transferred);
131       buffers_.set_max_size(detail::adapt_completion_condition_result(
132             completion_condition_(ec, total_transferred_)));
133       if (buffers_.begin() == buffers_.end())
134       {
135         handler_(ec, total_transferred_);
136       }
137       else
138       {
139         stream_.async_write_some(buffers_, *this);
140       }
141     }
143   //private:
144     AsyncWriteStream& stream_;
145     buffers_type buffers_;
146     std::size_t total_transferred_;
147     CompletionCondition completion_condition_;
148     WriteHandler handler_;
149   };
151   template <typename AsyncWriteStream, typename ConstBufferSequence,
152       typename CompletionCondition, typename WriteHandler>
153   inline void* asio_handler_allocate(std::size_t size,
154       write_handler<AsyncWriteStream, ConstBufferSequence,
155         CompletionCondition, WriteHandler>* this_handler)
156   {
157     return boost_asio_handler_alloc_helpers::allocate(
158         size, &this_handler->handler_);
159   }
161   template <typename AsyncWriteStream, typename ConstBufferSequence,
162       typename CompletionCondition, typename WriteHandler>
163   inline void asio_handler_deallocate(void* pointer, std::size_t size,
164       write_handler<AsyncWriteStream, ConstBufferSequence,
165         CompletionCondition, WriteHandler>* this_handler)
166   {
167     boost_asio_handler_alloc_helpers::deallocate(
168         pointer, size, &this_handler->handler_);
169   }
171   template <typename Function, typename AsyncWriteStream,
172       typename ConstBufferSequence, typename CompletionCondition,
173       typename WriteHandler>
174   inline void asio_handler_invoke(const Function& function,
175       write_handler<AsyncWriteStream, ConstBufferSequence,
176         CompletionCondition, WriteHandler>* this_handler)
177   {
178     boost_asio_handler_invoke_helpers::invoke(
179         function, &this_handler->handler_);
180   }
181 } // namespace detail
183 template <typename AsyncWriteStream, typename ConstBufferSequence,
184   typename CompletionCondition, typename WriteHandler>
185 inline void async_write(AsyncWriteStream& s, const ConstBufferSequence& buffers,
186     CompletionCondition completion_condition, WriteHandler handler)
188   boost::asio::detail::consuming_buffers<
189     const_buffer, ConstBufferSequence> tmp(buffers);
191   boost::system::error_code ec;
192   std::size_t total_transferred = 0;
193   tmp.set_max_size(detail::adapt_completion_condition_result(
194         completion_condition(ec, total_transferred)));
195   if (tmp.begin() == tmp.end())
196   {
197     s.get_io_service().post(detail::bind_handler(
198           handler, ec, total_transferred));
199     return;
200   }
202   s.async_write_some(tmp,
203       detail::write_handler<AsyncWriteStream, ConstBufferSequence,
204         CompletionCondition, WriteHandler>(
205           s, tmp, completion_condition, handler));
208 template <typename AsyncWriteStream, typename ConstBufferSequence,
209     typename WriteHandler>
210 inline void async_write(AsyncWriteStream& s, const ConstBufferSequence& buffers,
211     WriteHandler handler)
213   async_write(s, buffers, transfer_all(), handler);
216 namespace detail
218   template <typename AsyncWriteStream, typename Allocator,
219       typename WriteHandler>
220   class write_streambuf_handler
221   {
222   public:
223     write_streambuf_handler(boost::asio::basic_streambuf<Allocator>& streambuf,
224         WriteHandler handler)
225       : streambuf_(streambuf),
226         handler_(handler)
227     {
228     }
230     void operator()(const boost::system::error_code& ec,
231         std::size_t bytes_transferred)
232     {
233       streambuf_.consume(bytes_transferred);
234       handler_(ec, bytes_transferred);
235     }
237   //private:
238     boost::asio::basic_streambuf<Allocator>& streambuf_;
239     WriteHandler handler_;
240   };
242   template <typename AsyncWriteStream, typename Allocator,
243       typename WriteHandler>
244   inline void* asio_handler_allocate(std::size_t size,
245       write_streambuf_handler<AsyncWriteStream,
246         Allocator, WriteHandler>* this_handler)
247   {
248     return boost_asio_handler_alloc_helpers::allocate(
249         size, &this_handler->handler_);
250   }
252   template <typename AsyncWriteStream, typename Allocator,
253       typename WriteHandler>
254   inline void asio_handler_deallocate(void* pointer, std::size_t size,
255       write_streambuf_handler<AsyncWriteStream,
256         Allocator, WriteHandler>* this_handler)
257   {
258     boost_asio_handler_alloc_helpers::deallocate(
259         pointer, size, &this_handler->handler_);
260   }
262   template <typename Function, typename AsyncWriteStream, typename Allocator,
263       typename WriteHandler>
264   inline void asio_handler_invoke(const Function& function,
265       write_streambuf_handler<AsyncWriteStream,
266         Allocator, WriteHandler>* this_handler)
267   {
268     boost_asio_handler_invoke_helpers::invoke(
269         function, &this_handler->handler_);
270   }
271 } // namespace detail
273 template <typename AsyncWriteStream, typename Allocator,
274     typename CompletionCondition, typename WriteHandler>
275 inline void async_write(AsyncWriteStream& s,
276     boost::asio::basic_streambuf<Allocator>& b,
277     CompletionCondition completion_condition, WriteHandler handler)
279   async_write(s, b.data(), completion_condition,
280       detail::write_streambuf_handler<
281         AsyncWriteStream, Allocator, WriteHandler>(b, handler));
284 template <typename AsyncWriteStream, typename Allocator, typename WriteHandler>
285 inline void async_write(AsyncWriteStream& s,
286     boost::asio::basic_streambuf<Allocator>& b, WriteHandler handler)
288   async_write(s, b, transfer_all(), handler);
291 } // namespace asio
292 } // namespace boost
294 #include <boost/asio/detail/pop_options.hpp>
296 #endif // BOOST_ASIO_WRITE_IPP