BDE 4.39.x Production Release
Loading...
Searching...
No Matches
bdlbb_blobstreambuf.h
Go to the documentation of this file.
1/// @file bdlbb_blobstreambuf.h
2///
3/// The content of this file has been pre-processed for Doxygen.
4///
5
6
7// bdlbb_blobstreambuf.h -*-C++-*-
8#ifndef INCLUDED_BDLBB_BLOBSTREAMBUF
9#define INCLUDED_BDLBB_BLOBSTREAMBUF
10
11#include <bsls_ident.h>
12BSLS_IDENT("$Id: $")
13
14/// @defgroup bdlbb_blobstreambuf bdlbb_blobstreambuf
15/// @brief Provide blob implementing the `streambuf` interface.
16/// @addtogroup bdl
17/// @{
18/// @addtogroup bdlbb
19/// @{
20/// @addtogroup bdlbb_blobstreambuf
21/// @{
22///
23/// <h1> Outline </h1>
24/// * <a href="#bdlbb_blobstreambuf-purpose"> Purpose</a>
25/// * <a href="#bdlbb_blobstreambuf-classes"> Classes </a>
26/// * <a href="#bdlbb_blobstreambuf-description"> Description </a>
27///
28/// # Purpose {#bdlbb_blobstreambuf-purpose}
29/// Provide blob implementing the `streambuf` interface.
30///
31/// # Classes {#bdlbb_blobstreambuf-classes}
32///
33/// - bdlbb::InBlobStreamBuf: `bdlbb::Blob` input `streambuf`
34/// - bdlbb::OutBlobStreamBuf: `bdlbb::Blob` output `streambuf`
35///
36/// @see bdlbb_blob
37///
38/// # Description {#bdlbb_blobstreambuf-description}
39/// This component implements the input and output
40/// `bsl::basic_streambuf` protocol using a user-supplied `bdlbb::Blob`. Method
41/// names necessarily correspond to the protocol-specified method names. Refer
42/// to the C++ Standard, Section 27.5.2, for a full specification of the
43/// interface.
44///
45/// A `bdlbb::Blob` is an indexed sequence of `bdlbb::BlobBuffer` of potentially
46/// different sizes. The number of buffers in the sequence can increase or
47/// decrease, but the order of the buffers cannot change. Therefore, the blob
48/// behaves logically as a single indexed buffer. `bdlbb::InBlobStreamBuf` and
49/// `bdlbb::OutBlobStreamBuf` can therefore respectively read from and write to
50/// this buffer as if there were a single continuous index.
51/// @}
52/** @} */
53/** @} */
54
55/** @addtogroup bdl
56 * @{
57 */
58/** @addtogroup bdlbb
59 * @{
60 */
61/** @addtogroup bdlbb_blobstreambuf
62 * @{
63 */
64
65#include <bdlscm_version.h>
66
67#include <bdlbb_blob.h>
68
69#include <bsls_assert.h>
70#include <bsls_keyword.h>
71#include <bsls_review.h>
72
73#include <bsl_ios.h> // for 'bsl::streamsize'
74#include <bsl_streambuf.h>
75#include <bsl_cstddef.h> // bsl::size_t
76
77
78namespace bdlbb { class Blob; }
79namespace bdlbb {
80
81 // =====================
82 // class InBlobStreamBuf
83 // =====================
84
85/// This class implements the input functionality of the @ref basic_streambuf
86/// protocol, using a client-supplied `bdlbb::Blob`.
87///
88/// See @ref bdlbb_blobstreambuf
89class InBlobStreamBuf : public bsl::streambuf {
90
91 // PRIVATE TYPES
92 typedef bsl::ios_base ios_base;
93
94 // DATA
95 const bdlbb::Blob *d_blob_p; // "streamed" blob (held)
96 int d_getBufferIndex; // index of current buffer
97 int d_previousBuffersLength; // length of buffers before the
98 // current one
99
100 private:
101 // NOT IMPLEMENTED
103 InBlobStreamBuf& operator=(const InBlobStreamBuf&);
104
105 private:
106 // PRIVATE MANIPULATORS
107
108 /// Set the current location to the specified `position`.
109 void setGetPosition(bsl::size_t position);
110
111 // PRIVATE ACCESSORS
112
113 /// Check this object's invariant.
114 int checkInvariant() const;
115
116 protected:
117 // PROTECTED VIRTUAL FUNCTIONS
118
119 /// Return `traits_type::eof()` unconditionally.
120 int_type overflow(int_type c = bsl::streambuf::traits_type::eof())
122
123 /// Adjust the underlying blob and put the optionally specified
124 /// character `c` at the newly valid `gptr()`. Return `c` (or
125 /// `~traits_type::eof` if `c == traits_type::eof`) on success, and
126 /// `traits_type::eof()` otherwise.
127 int_type pbackfail(int_type c = bsl::streambuf::traits_type::eof())
129
130 /// Set the location from which the next I/O operation indicated by the
131 /// optionally specified `which` mode will occur to the specified
132 /// `offset` position from the location indicated by the specified
133 /// `fixedPosition`. Return the new offset on success, and `off_type(-1)` otherwise. `offset` may be negative.
134 ///
135 /// \note Note that this
136 /// method will fail if `bsl::ios_base::out` is set.
137 pos_type seekoff(
138 off_type offset,
139 bsl::ios_base::seekdir fixedPosition,
140 bsl::ios_base::openmode which = bsl::ios_base::in | bsl::ios_base::out)
142
143 /// Set the location from which the next I/O operation indicated by the
144 /// optionally specified `which` mode will occur to the specified
145 /// `position`. Return `position` on success, and `off_type(-1)` otherwise.
146 ///
147 /// \note Note that this method will fail if `bsl::ios_base::out`
148 /// is set.
149 pos_type seekpos(
150 pos_type position,
151 bsl::ios_base::openmode which = bsl::ios_base::in | bsl::ios_base::out)
153
154 /// Return the number of characters currently available for reading from
155 /// this stream buffer, or 0 if there are none.
157
158 /// Return 0 unconditionally.
160
161 /// Adjust the underlying blob so that the next read position is valid.
162 /// Return the character at `gptr()` on success and `traits_type::eof()`
163 /// otherwise.
165
166 /// Read the specified `numChars` to the specified `destination`.
167 /// Return the number of characters successfully read.
168 ///
169 /// \pre The behavior is undefined unless 0 <= `numChars`.
170 bsl::streamsize xsgetn(char_type *destination,
171 bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE;
172
173 /// Return 0 unconditionally.
174 bsl::streamsize xsputn(const char_type *source,
175 bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE;
176
177 public:
178 // CREATORS
179
180 /// Create a `BlobStreamBuf` using the specified `blob`.
181 ///
182 /// \pre The behavior is undefined unless `blob` remains valid and externally unmodified
183 /// for the lifetime of this `streambuf`.
184 explicit InBlobStreamBuf(const bdlbb::Blob *blob);
185
186 /// Destroy this stream buffer.
188
189 // MANIPULATORS
190
191 /// Reset the get areas. Optionally set the underlying `bdlbb::Blob`
192 /// value to the optionally specified `blob` if `blob` is not 0.
193 ///
194 /// \pre The behavior is undefined unless `blob` remains valid and externally
195 /// unmodified for the lifetime of this `streambuf`.
196 void reset(const bdlbb::Blob *blob = 0);
197
198 // ACCESSORS
199
200 /// Return the index of the current buffer.
201 ///
202 /// \pre The behavior is undefined unless the "streamed" blob has at least one buffer.
203 int currentBufferIndex() const;
204
205 /// Return the address of the blob held by this stream buffer.
206 const bdlbb::Blob *data() const;
207
208 /// Return the number of bytes contained in the buffers located before the current one.
209 ///
210 /// \pre The behavior is undefined unless the "streamed"
211 /// blob has at least one buffer.
212 int previousBuffersLength() const;
213};
214
215 // ======================
216 // class OutBlobStreamBuf
217 // ======================
218
219/// This class implements the output functionality of the @ref basic_streambuf
220/// protocol, using a client-supplied `bdlbb::Blob`.
221///
222/// See @ref bdlbb_blobstreambuf
223class OutBlobStreamBuf : public bsl::streambuf {
224
225 // PRIVATE TYPES
226 typedef bsl::ios_base ios_base;
227
228 // DATA
229 bdlbb::Blob *d_blob_p; // "streamed" blob (held)
230 int d_putBufferIndex; // index of current buffer
231 int d_previousBuffersLength; // length of buffers before
232
233 private:
234 // NOT IMPLEMENTED
236 OutBlobStreamBuf& operator=(const OutBlobStreamBuf&);
237
238 private:
239 // PRIVATE MANIPULATORS
240
241 /// Set the current location to the specified `position`.
242 void setPutPosition(bsl::size_t position);
243
244 // PRIVATE ACCESSORS
245
246 /// Check this object's invariants and return 0.
247 int checkInvariant() const;
248
249 protected:
250 // PROTECTED VIRTUAL FUNCTIONS
251
252 /// Append the optionally specified character `c` to this streambuf, and
253 /// return `c`. By default, `traits_type::eof()` is appended.
254 int_type overflow(int_type c = bsl::streambuf::traits_type::eof())
256
257 /// Return `traits_type::eof()` unconditionally.
258 int_type pbackfail(int_type c = bsl::streambuf::traits_type::eof())
260
261 /// Set the location from which the next I/O operation indicated by the
262 /// optionally specified `which` mode will occur to the specified
263 /// `offset` position from the location indicated by the specified
264 /// `fixedPosition`. Return the new offset on success, and `off_type(-1)` otherwise. `offset` may be negative.
265 ///
266 /// \note Note that this
267 /// method will fail if `bsl::ios_base::in` is set.
268 pos_type seekoff(
269 off_type offset,
270 bsl::ios_base::seekdir fixedPosition,
271 bsl::ios_base::openmode which = bsl::ios_base::in | bsl::ios_base::out)
273
274 /// Set the location from which the next I/O operation indicated by the
275 /// optionally specified `which` mode will occur to the specified
276 /// `position`. Return `position` on success, and `off_type(-1)` otherwise.
277 ///
278 /// \note Note that this method will fail if `bsl::ios_base::in`
279 /// is set.
280 pos_type seekpos(
281 pos_type position,
282 bsl::ios_base::openmode which = bsl::ios_base::in | bsl::ios_base::out)
284
285 /// Return 0 unconditionally.
287
288 /// Synchronize the put position in the blob of this stream buffer.
289 /// Return 0 unconditionally.
291
292 /// Return `traits_type::eof()` unconditionally.
294
295 /// Return 0 unconditionally.
296 bsl::streamsize xsgetn(char_type *destination,
297 bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE;
298
299 /// Copy the specified `numChars` from the specified `source` to the
300 /// blob held by this streambuf, starting at the current put area location.
301 ///
302 /// \pre The behavior is undefined unless 0 <= `numChars`.
303 bsl::streamsize xsputn(const char_type *source,
304 bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE;
305
306 public:
307 // CREATORS
308
309 /// Create a `OutBlobStreamBuf` using the specified `blob`, and set the
310 /// location at which the next write operation will occur to `blob->length()`.
311 ///
312 /// \pre The behavior is undefined unless `blob` remains
313 /// valid and externally unmodified for the lifetime of this
314 /// `streambuf`.
315 explicit OutBlobStreamBuf(bdlbb::Blob *blob);
316
317 /// Destroy this stream buffer.
319
320 // MANIPULATORS
321
322 /// Return the address of the blob held by this stream buffer.
323 bdlbb::Blob *data();
324
325 /// Reset the put position of this buffer to the first location,
326 /// available for writing in the underlying `bdlbb::Blob`. Optionally
327 /// specify a `blob` used to change current underlying `bdlbb::Blob` value for.
328 ///
329 /// \pre The behavior is undefined unless `blob` remains valid
330 /// and externally unmodified for the lifetime of this `streambuf`.
331 void reset(bdlbb::Blob *blob = 0);
332
333 // ACCESSORS
334
335 /// Return the index of the current buffer.
336 ///
337 /// \pre The behavior is undefined unless the "streamed" blob has at least one buffer.
338 int currentBufferIndex() const;
339
340 /// Return the address of the blob held by this stream buffer.
341 const bdlbb::Blob *data() const;
342
343 /// Return the number of bytes contained in the buffers located before the current one.
344 ///
345 /// \pre The behavior is undefined unless the "streamed"
346 /// blob has at least one buffer.
347 int previousBuffersLength() const;
348};
349
350// ============================================================================
351// INLINE DEFINITIONS
352// ============================================================================
353
354 // =====================
355 // class InBlobStreamBuf
356 // =====================
357
358// MANIPULATORS
359inline
360void InBlobStreamBuf::reset(const bdlbb::Blob *blob)
361{
362 if (blob) {
363 d_blob_p = blob;
364 d_getBufferIndex = 0;
365 d_previousBuffersLength = 0;
366 setg(0, 0, 0);
367 if (0 == d_blob_p->length()) {
368 return; // RETURN
369 }
370 }
371 setGetPosition(0);
372}
373
374// ACCESSORS
375inline
377{
378 BSLS_ASSERT(d_getBufferIndex < d_blob_p->numBuffers());
379 return d_getBufferIndex;
380}
381
382inline
384{
385 return d_blob_p;
386}
387
388inline
390{
391 return d_previousBuffersLength;
392}
393
394 // ======================
395 // class OutBlobStreamBuf
396 // ======================
397
398// MANIPULATORS
399inline
401{
402 return d_blob_p;
403}
404
405inline
407{
408 if (blob) {
409 d_blob_p = blob;
410 d_putBufferIndex = 0;
411 d_previousBuffersLength = 0;
412 setp(0, 0);
413 if (0 == d_blob_p->totalSize()) {
414 return; // RETURN
415 }
416 }
417 setPutPosition(d_blob_p->length());
418}
419
420// ACCESSORS
421inline
423{
424 BSLS_ASSERT(d_putBufferIndex < d_blob_p->numBuffers());
425 return d_putBufferIndex;
426}
427
428inline
430{
431 return d_blob_p;
432}
433
434inline
436{
437 return d_previousBuffersLength;
438}
439} // close package namespace
440
441
442
443#endif
444
445// ----------------------------------------------------------------------------
446// Copyright 2018 Bloomberg Finance L.P.
447//
448// Licensed under the Apache License, Version 2.0 (the "License");
449// you may not use this file except in compliance with the License.
450// You may obtain a copy of the License at
451//
452// http://www.apache.org/licenses/LICENSE-2.0
453//
454// Unless required by applicable law or agreed to in writing, software
455// distributed under the License is distributed on an "AS IS" BASIS,
456// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
457// See the License for the specific language governing permissions and
458// limitations under the License.
459// ----------------------------- END-OF-FILE ----------------------------------
460
461/** @} */
462/** @} */
463/** @} */
Definition bdlbb_blob.h:645
int length() const
Return the length of this blob.
Definition bdlbb_blob.h:1253
int totalSize() const
Definition bdlbb_blob.h:1271
Definition bdlbb_blobstreambuf.h:89
void reset(const bdlbb::Blob *blob=0)
Definition bdlbb_blobstreambuf.h:360
bsl::streamsize xsgetn(char_type *destination, bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE
int_type pbackfail(int_type c=bsl::streambuf::traits_type::eof()) BSLS_KEYWORD_OVERRIDE
const bdlbb::Blob * data() const
Return the address of the blob held by this stream buffer.
Definition bdlbb_blobstreambuf.h:383
int_type overflow(int_type c=bsl::streambuf::traits_type::eof()) BSLS_KEYWORD_OVERRIDE
Return traits_type::eof() unconditionally.
int sync() BSLS_KEYWORD_OVERRIDE
Return 0 unconditionally.
bsl::streamsize showmanyc() BSLS_KEYWORD_OVERRIDE
pos_type seekoff(off_type offset, bsl::ios_base::seekdir fixedPosition, bsl::ios_base::openmode which=bsl::ios_base::in|bsl::ios_base::out) BSLS_KEYWORD_OVERRIDE
pos_type seekpos(pos_type position, bsl::ios_base::openmode which=bsl::ios_base::in|bsl::ios_base::out) BSLS_KEYWORD_OVERRIDE
int_type underflow() BSLS_KEYWORD_OVERRIDE
int currentBufferIndex() const
Definition bdlbb_blobstreambuf.h:376
int previousBuffersLength() const
Definition bdlbb_blobstreambuf.h:389
bsl::streamsize xsputn(const char_type *source, bsl::streamsize numChars) BSLS_KEYWORD_OVERRIDE
Return 0 unconditionally.
Definition bdlbb_blobstreambuf.h:223
int currentBufferIndex() const
Definition bdlbb_blobstreambuf.h:422
int previousBuffersLength() const
Definition bdlbb_blobstreambuf.h:435
int_type overflow(int_type c=bsl::streambuf::traits_type::eof()) BSLS_KEYWORD_OVERRIDE
void reset(bdlbb::Blob *blob=0)
Definition bdlbb_blobstreambuf.h:406
bdlbb::Blob * data()
Return the address of the blob held by this stream buffer.
Definition bdlbb_blobstreambuf.h:400
#define BSLS_ASSERT(X)
Definition bsls_assert.h:1976
#define BSLS_IDENT(str)
BSLS_IDENT() - insert string into .comment binary segment (if supported)
Definition bsls_ident.h:238
#define BSLS_KEYWORD_OVERRIDE
Definition bsls_keyword.h:695
Definition bdlbb_blob.h:437
Definition bdlat_valuetypefunctions.h:939