Imported Upstream version 1.72.0
[platform/upstream/boost.git] / doc / html / boost_asio / overview / core / buffers.html
1 <html>
2 <head>
3 <meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
4 <title>Buffers</title>
5 <link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
6 <meta name="generator" content="DocBook XSL Stylesheets V1.79.1">
7 <link rel="home" href="../../../boost_asio.html" title="Boost.Asio">
8 <link rel="up" href="../core.html" title="Core Concepts and Functionality">
9 <link rel="prev" href="strands.html" title="Strands: Use Threads Without Explicit Locking">
10 <link rel="next" href="streams.html" title="Streams, Short Reads and Short Writes">
11 </head>
12 <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
13 <table cellpadding="2" width="100%"><tr>
14 <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
15 <td align="center"><a href="../../../../../index.html">Home</a></td>
16 <td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
17 <td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
18 <td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
19 <td align="center"><a href="../../../../../more/index.htm">More</a></td>
20 </tr></table>
21 <hr>
22 <div class="spirit-nav">
23 <a accesskey="p" href="strands.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../core.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../../boost_asio.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="streams.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
24 </div>
25 <div class="section">
26 <div class="titlepage"><div><div><h4 class="title">
27 <a name="boost_asio.overview.core.buffers"></a><a class="link" href="buffers.html" title="Buffers">Buffers</a>
28 </h4></div></div></div>
29 <p>
30           Fundamentally, I/O involves the transfer of data to and from contiguous
31           regions of memory, called buffers. These buffers can be simply expressed
32           as a tuple consisting of a pointer and a size in bytes. However, to allow
33           the development of efficient network applications, Boost.Asio includes
34           support for scatter-gather operations. These operations involve one or
35           more buffers:
36         </p>
37 <div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
38 <li class="listitem">
39               A scatter-read receives data into multiple buffers.
40             </li>
41 <li class="listitem">
42               A gather-write transmits multiple buffers.
43             </li>
44 </ul></div>
45 <p>
46           Therefore we require an abstraction to represent a collection of buffers.
47           The approach used in Boost.Asio is to define a type (actually two types)
48           to represent a single buffer. These can be stored in a container, which
49           may be passed to the scatter-gather operations.
50         </p>
51 <p>
52           In addition to specifying buffers as a pointer and size in bytes, Boost.Asio
53           makes a distinction between modifiable memory (called mutable) and non-modifiable
54           memory (where the latter is created from the storage for a const-qualified
55           variable). These two types could therefore be defined as follows:
56         </p>
57 <pre class="programlisting"><span class="keyword">typedef</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special">&lt;</span><span class="keyword">void</span><span class="special">*,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">size_t</span><span class="special">&gt;</span> <span class="identifier">mutable_buffer</span><span class="special">;</span>
58 <span class="keyword">typedef</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special">&lt;</span><span class="keyword">const</span> <span class="keyword">void</span><span class="special">*,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">size_t</span><span class="special">&gt;</span> <span class="identifier">const_buffer</span><span class="special">;</span>
59 </pre>
60 <p>
61           Here, a mutable_buffer would be convertible to a const_buffer, but conversion
62           in the opposite direction is not valid.
63         </p>
64 <p>
65           However, Boost.Asio does not use the above definitions as-is, but instead
66           defines two classes: <code class="computeroutput"><span class="identifier">mutable_buffer</span></code>
67           and <code class="computeroutput"><span class="identifier">const_buffer</span></code>. The goal
68           of these is to provide an opaque representation of contiguous memory, where:
69         </p>
70 <div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
71 <li class="listitem">
72               Types behave as std::pair would in conversions. That is, a <code class="computeroutput"><span class="identifier">mutable_buffer</span></code> is convertible to
73               a <code class="computeroutput"><span class="identifier">const_buffer</span></code>, but
74               the opposite conversion is disallowed.
75             </li>
76 <li class="listitem">
77               There is protection against buffer overruns. Given a buffer instance,
78               a user can only create another buffer representing the same range of
79               memory or a sub-range of it. To provide further safety, the library
80               also includes mechanisms for automatically determining the size of
81               a buffer from an array, <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">array</span></code>
82               or <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">vector</span></code> of POD elements, or from a
83               <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>.
84             </li>
85 <li class="listitem">
86               The underlying memory is explicitly accessed using the <code class="computeroutput"><span class="identifier">data</span><span class="special">()</span></code>
87               member function. In general an application should never need to do
88               this, but it is required by the library implementation to pass the
89               raw memory to the underlying operating system functions.
90             </li>
91 </ul></div>
92 <p>
93           Finally, multiple buffers can be passed to scatter-gather operations (such
94           as <a class="link" href="../../reference/read.html" title="read">read()</a> or <a class="link" href="../../reference/write.html" title="write">write()</a>)
95           by putting the buffer objects into a container. The <code class="computeroutput"><span class="identifier">MutableBufferSequence</span></code>
96           and <code class="computeroutput"><span class="identifier">ConstBufferSequence</span></code>
97           concepts have been defined so that containers such as <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">vector</span></code>,
98           <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span></code>, <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">array</span></code>
99           or <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">array</span></code> can be used.
100         </p>
101 <h6>
102 <a name="boost_asio.overview.core.buffers.h0"></a>
103           <span class="phrase"><a name="boost_asio.overview.core.buffers.streambuf_for_integration_with_iostreams"></a></span><a class="link" href="buffers.html#boost_asio.overview.core.buffers.streambuf_for_integration_with_iostreams">Streambuf
104           for Integration with Iostreams</a>
105         </h6>
106 <p>
107           The class <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">basic_streambuf</span></code> is derived from <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">basic_streambuf</span></code> to associate the input
108           sequence and output sequence with one or more objects of some character
109           array type, whose elements store arbitrary values. These character array
110           objects are internal to the streambuf object, but direct access to the
111           array elements is provided to permit them to be used with I/O operations,
112           such as the send or receive operations of a socket:
113         </p>
114 <div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
115 <li class="listitem">
116               The input sequence of the streambuf is accessible via the <a class="link" href="../../reference/basic_streambuf/data.html" title="basic_streambuf::data">data()</a>
117               member function. The return type of this function meets the <code class="computeroutput"><span class="identifier">ConstBufferSequence</span></code> requirements.
118             </li>
119 <li class="listitem">
120               The output sequence of the streambuf is accessible via the <a class="link" href="../../reference/basic_streambuf/prepare.html" title="basic_streambuf::prepare">prepare()</a>
121               member function. The return type of this function meets the <code class="computeroutput"><span class="identifier">MutableBufferSequence</span></code> requirements.
122             </li>
123 <li class="listitem">
124               Data is transferred from the front of the output sequence to the back
125               of the input sequence by calling the <a class="link" href="../../reference/basic_streambuf/commit.html" title="basic_streambuf::commit">commit()</a>
126               member function.
127             </li>
128 <li class="listitem">
129               Data is removed from the front of the input sequence by calling the
130               <a class="link" href="../../reference/basic_streambuf/consume.html" title="basic_streambuf::consume">consume()</a>
131               member function.
132             </li>
133 </ul></div>
134 <p>
135           The streambuf constructor accepts a <code class="computeroutput"><span class="identifier">size_t</span></code>
136           argument specifying the maximum of the sum of the sizes of the input sequence
137           and output sequence. Any operation that would, if successful, grow the
138           internal data beyond this limit will throw a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">length_error</span></code>
139           exception.
140         </p>
141 <h6>
142 <a name="boost_asio.overview.core.buffers.h1"></a>
143           <span class="phrase"><a name="boost_asio.overview.core.buffers.bytewise_traversal_of_buffer_sequences"></a></span><a class="link" href="buffers.html#boost_asio.overview.core.buffers.bytewise_traversal_of_buffer_sequences">Bytewise
144           Traversal of Buffer Sequences</a>
145         </h6>
146 <p>
147           The <code class="computeroutput"><span class="identifier">buffers_iterator</span><span class="special">&lt;&gt;</span></code>
148           class template allows buffer sequences (i.e. types meeting <code class="computeroutput"><span class="identifier">MutableBufferSequence</span></code> or <code class="computeroutput"><span class="identifier">ConstBufferSequence</span></code> requirements) to
149           be traversed as though they were a contiguous sequence of bytes. Helper
150           functions called buffers_begin() and buffers_end() are also provided, where
151           the buffers_iterator&lt;&gt; template parameter is automatically deduced.
152         </p>
153 <p>
154           As an example, to read a single line from a socket and into a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>, you may write:
155         </p>
156 <pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">streambuf</span> <span class="identifier">sb</span><span class="special">;</span>
157 <span class="special">...</span>
158 <span class="identifier">std</span><span class="special">::</span><span class="identifier">size_t</span> <span class="identifier">n</span> <span class="special">=</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">read_until</span><span class="special">(</span><span class="identifier">sock</span><span class="special">,</span> <span class="identifier">sb</span><span class="special">,</span> <span class="char">'\n'</span><span class="special">);</span>
159 <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">streambuf</span><span class="special">::</span><span class="identifier">const_buffers_type</span> <span class="identifier">bufs</span> <span class="special">=</span> <span class="identifier">sb</span><span class="special">.</span><span class="identifier">data</span><span class="special">();</span>
160 <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">line</span><span class="special">(</span>
161     <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">buffers_begin</span><span class="special">(</span><span class="identifier">bufs</span><span class="special">),</span>
162     <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">buffers_begin</span><span class="special">(</span><span class="identifier">bufs</span><span class="special">)</span> <span class="special">+</span> <span class="identifier">n</span><span class="special">);</span>
163 </pre>
164 <h6>
165 <a name="boost_asio.overview.core.buffers.h2"></a>
166           <span class="phrase"><a name="boost_asio.overview.core.buffers.buffer_debugging"></a></span><a class="link" href="buffers.html#boost_asio.overview.core.buffers.buffer_debugging">Buffer
167           Debugging</a>
168         </h6>
169 <p>
170           Some standard library implementations, such as the one that ships with
171           Microsoft Visual C++ 8.0 and later, provide a feature called iterator debugging.
172           What this means is that the validity of iterators is checked at runtime.
173           If a program tries to use an iterator that has been invalidated, an assertion
174           will be triggered. For example:
175         </p>
176 <pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="identifier">v</span><span class="special">(</span><span class="number">1</span><span class="special">)</span>
177 <span class="identifier">std</span><span class="special">::</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;::</span><span class="identifier">iterator</span> <span class="identifier">i</span> <span class="special">=</span> <span class="identifier">v</span><span class="special">.</span><span class="identifier">begin</span><span class="special">();</span>
178 <span class="identifier">v</span><span class="special">.</span><span class="identifier">clear</span><span class="special">();</span> <span class="comment">// invalidates iterators</span>
179 <span class="special">*</span><span class="identifier">i</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span> <span class="comment">// assertion!</span>
180 </pre>
181 <p>
182           Boost.Asio takes advantage of this feature to add buffer debugging. Consider
183           the following code:
184         </p>
185 <pre class="programlisting"><span class="keyword">void</span> <span class="identifier">dont_do_this</span><span class="special">()</span>
186 <span class="special">{</span>
187  <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span> <span class="special">=</span> <span class="string">"Hello, world!"</span><span class="special">;</span>
188  <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">async_write</span><span class="special">(</span><span class="identifier">sock</span><span class="special">,</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">asio</span><span class="special">::</span><span class="identifier">buffer</span><span class="special">(</span><span class="identifier">msg</span><span class="special">),</span> <span class="identifier">my_handler</span><span class="special">);</span>
189 <span class="special">}</span>
190 </pre>
191 <p>
192           When you call an asynchronous read or write you need to ensure that the
193           buffers for the operation are valid until the completion handler is called.
194           In the above example, the buffer is the <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>
195           variable <code class="computeroutput"><span class="identifier">msg</span></code>. This variable
196           is on the stack, and so it goes out of scope before the asynchronous operation
197           completes. If you're lucky then the application will crash, but random
198           failures are more likely.
199         </p>
200 <p>
201           When buffer debugging is enabled, Boost.Asio stores an iterator into the
202           string until the asynchronous operation completes, and then dereferences
203           it to check its validity. In the above example you would observe an assertion
204           failure just before Boost.Asio tries to call the completion handler.
205         </p>
206 <p>
207           This feature is automatically made available for Microsoft Visual Studio
208           8.0 or later and for GCC when <code class="computeroutput"><span class="identifier">_GLIBCXX_DEBUG</span></code>
209           is defined. There is a performance cost to this checking, so buffer debugging
210           is only enabled in debug builds. For other compilers it may be enabled
211           by defining <code class="computeroutput"><span class="identifier">BOOST_ASIO_ENABLE_BUFFER_DEBUGGING</span></code>.
212           It can also be explicitly disabled by defining <code class="computeroutput"><span class="identifier">BOOST_ASIO_DISABLE_BUFFER_DEBUGGING</span></code>.
213         </p>
214 <h6>
215 <a name="boost_asio.overview.core.buffers.h3"></a>
216           <span class="phrase"><a name="boost_asio.overview.core.buffers.see_also"></a></span><a class="link" href="buffers.html#boost_asio.overview.core.buffers.see_also">See
217           Also</a>
218         </h6>
219 <p>
220           <a class="link" href="../../reference/buffer.html" title="buffer">buffer</a>, <a class="link" href="../../reference/buffers_begin.html" title="buffers_begin">buffers_begin</a>,
221           <a class="link" href="../../reference/buffers_end.html" title="buffers_end">buffers_end</a>, <a class="link" href="../../reference/buffers_iterator.html" title="buffers_iterator">buffers_iterator</a>,
222           <a class="link" href="../../reference/const_buffer.html" title="const_buffer">const_buffer</a>,
223           <a class="link" href="../../reference/const_buffers_1.html" title="const_buffers_1">const_buffers_1</a>,
224           <a class="link" href="../../reference/mutable_buffer.html" title="mutable_buffer">mutable_buffer</a>,
225           <a class="link" href="../../reference/mutable_buffers_1.html" title="mutable_buffers_1">mutable_buffers_1</a>,
226           <a class="link" href="../../reference/streambuf.html" title="streambuf">streambuf</a>, <a class="link" href="../../reference/ConstBufferSequence.html" title="Constant buffer sequence requirements">ConstBufferSequence</a>,
227           <a class="link" href="../../reference/MutableBufferSequence.html" title="Mutable buffer sequence requirements">MutableBufferSequence</a>,
228           <a class="link" href="../../examples/cpp03_examples.html#boost_asio.examples.cpp03_examples.buffers">buffers example
229           (C++03)</a>, <a class="link" href="../../examples/cpp11_examples.html#boost_asio.examples.cpp11_examples.buffers">buffers
230           example (c++11)</a>.
231         </p>
232 </div>
233 <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
234 <td align="left"></td>
235 <td align="right"><div class="copyright-footer">Copyright &#169; 2003-2019 Christopher M. Kohlhoff<p>
236         Distributed under the Boost Software License, Version 1.0. (See accompanying
237         file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
238       </p>
239 </div></td>
240 </tr></table>
241 <hr>
242 <div class="spirit-nav">
243 <a accesskey="p" href="strands.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../core.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../../boost_asio.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="streams.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
244 </div>
245 </body>
246 </html>