BDE 4.39.x Production Release
Loading...
Searching...
No Matches
bslstl_simplepool.h
Go to the documentation of this file.
1/// @file bslstl_simplepool.h
2///
3/// The content of this file has been pre-processed for Doxygen.
4///
5
6
7// bslstl_simplepool.h -*-C++-*-
8#ifndef INCLUDED_BSLSTL_SIMPLEPOOL
9#define INCLUDED_BSLSTL_SIMPLEPOOL
10
11#include <bsls_ident.h>
12BSLS_IDENT("$Id: $")
13
14/// @defgroup bslstl_simplepool bslstl_simplepool
15/// @brief Provide efficient allocation of memory blocks for a specific type.
16/// @addtogroup bsl
17/// @{
18/// @addtogroup bslstl
19/// @{
20/// @addtogroup bslstl_simplepool
21/// @{
22///
23/// <h1> Outline </h1>
24/// * <a href="#bslstl_simplepool-purpose"> Purpose</a>
25/// * <a href="#bslstl_simplepool-classes"> Classes </a>
26/// * <a href="#bslstl_simplepool-description"> Description </a>
27/// * <a href="#bslstl_simplepool-comparison-with-bdema_pool"> Comparison with bdema_Pool </a>
28/// * <a href="#bslstl_simplepool-usage"> Usage </a>
29/// * <a href="#bslstl_simplepool-example-1-creating-a-node-based-stack"> Example 1: Creating a Node-Based Stack </a>
30///
31/// # Purpose {#bslstl_simplepool-purpose}
32/// Provide efficient allocation of memory blocks for a specific type.
33///
34/// # Classes {#bslstl_simplepool-classes}
35///
36/// - bslstl::SimplePool: memory manager that allocates memory blocks for a type
37///
38/// @see bslstl_treenodepool, bdlma_pool
39///
40/// # Description {#bslstl_simplepool-description}
41/// This component implements a memory pool, `bslstl::SimplePool`,
42/// that allocates and manages memory blocks of for a parameterized type. A
43/// `bslstl::SimplePool` object maintains an internal linked list of
44/// free memory blocks, and dispenses one block for each `allocate` method
45/// invocation. When a memory block is deallocated, it is returned to the free
46/// list for potential reuse.
47///
48/// Whenever the linked list of free memory blocks is depleted,
49/// `bslstl::SimplePool` replenishes the list by first allocating a large,
50/// contiguous "chunk" of memory, then splitting the chunk into multiple memory
51/// blocks each having the `sizeof` the simple pool's parameterized type. A
52/// chunk and its constituent memory blocks can be depicted visually:
53/// @code
54/// +-----+--- memory blocks of uniform size for parameterized type
55/// | |
56/// ----- ----- ------------
57/// | | | ... |
58/// =====^=====^============
59///
60/// \___________ __________/
61/// V
62/// a "chunk"
63/// @endcode
64/// This pool implementation is simple because its allocation strategy is not
65/// configurable. The size of a chunk starts from 1 memory block, and doubles
66/// each time a chunk is allocated up to an implementation defined maximum
67/// number of blocks.
68///
69/// ## Comparison with bdema_Pool {#bslstl_simplepool-comparison-with-bdema_pool}
70///
71///
72/// There are a few differences between `bslstl::SimplePool` and `bdema_Pool`:
73/// 1. `bslstl::SimplePool` is parameterized on both allocator and type, which
74/// improve performance and memory usage in exchange for increase in code
75/// size.
76/// 2. `bslstl::SimplePool` uses the allocator through the use of
77/// `bsl::allocator_traits` (which is generally not relevant to non-container
78/// type.
79/// 3. `bslstl::SimplePool` is less configurable in order to achieve abstraction
80/// of allocation and improvement in performance.
81///
82/// Clients are encouraged to use `bdema_Pool` as `bslstl::SimplePool` is
83/// designed for node-based STL containers, and its pooling behavior may change
84/// according to the needs of those containers.
85///
86/// ## Usage {#bslstl_simplepool-usage}
87///
88///
89/// This section illustrates intended use for this component.
90///
91/// ### Example 1: Creating a Node-Based Stack {#bslstl_simplepool-example-1-creating-a-node-based-stack}
92///
93///
94/// Suppose that we want to implement a stack with a linked list. It is
95/// expensive to allocate memory every time a node is inserted. Therefore, we
96/// can use `SimplePool` to efficiently manage the memory for the list.
97///
98/// First, we define the class that implements the stack:
99/// @code
100/// /// This class defines a node-based stack of integers.
101/// template <class ALLOCATOR = bsl::allocator<int> >
102/// class my_Stack {
103///
104/// // PRIVATE TYPES
105///
106/// /// This `struct` implements a link data structure containing a
107/// /// value and a pointer to the next node.
108/// struct Node {
109///
110/// int d_value; // payload value
111/// Node *d_next_p; // pointer to the next node
112/// };
113///
114/// typedef bslstl::SimplePool<Node, ALLOCATOR> Pool;
115/// // Alias for memory pool.
116///
117/// private:
118/// // DATA
119/// Node *d_head_p; // pointer to the first node
120/// int d_size; // size of the stack
121/// Pool d_pool; // memory manager for the stack
122///
123/// public:
124/// // CREATORS
125///
126/// /// Create an empty `my_Stack` object. Optionally specify a
127/// /// `basicAllocator` used to supply memory. If `basicAllocator` is
128/// /// 0, the currently installed default allocator is used.
129/// my_Stack(const ALLOCATOR& allocator = ALLOCATOR());
130///
131/// // MANIPULATORS
132///
133/// /// Insert an element with the specified value to the top of this
134/// /// stack.
135/// void push(int value);
136///
137/// /// Remove the top element from this stack. The behavior is
138/// /// undefined unless `1 <= size()`.
139/// void pop();
140///
141/// // ACCESSORS
142///
143/// /// Return the value of the element on the top of this stack. The
144/// /// behavior is undefined unless `1 <= size()`.
145/// int top();
146///
147/// /// Return the number of elements in this stack.
148/// std::size_t size();
149/// };
150/// @endcode
151/// Now, we define the implementation of the stack. Notice how
152/// `bslstl::SimplePool` is used to allocate memory in `push` and deallocate
153/// memory in `pop`:
154/// @code
155/// // CREATORS
156/// template <class ALLOCATOR>
157/// my_Stack<ALLOCATOR>::my_Stack(const ALLOCATOR& allocator)
158/// : d_head_p(0)
159/// , d_size(0)
160/// , d_pool(allocator)
161/// {
162/// }
163///
164/// // MANIPULATORS
165/// template <class ALLOCATOR>
166/// void my_Stack<ALLOCATOR>::push(int value)
167/// {
168/// Node *newNode = d_pool.allocate();
169///
170/// newNode->d_value = value;
171/// newNode->d_next_p = d_head_p;
172/// d_head_p = newNode;
173///
174/// ++d_size;
175/// }
176///
177/// template <class ALLOCATOR>
178/// void my_Stack<ALLOCATOR>::pop()
179/// {
180/// BSLS_ASSERT(0 != size());
181///
182/// Node *n = d_head_p;
183/// d_head_p = d_head_p->d_next_p;
184/// d_pool.deallocate(n);
185/// --d_size;
186/// }
187///
188/// // ACCESSORS
189/// template <class ALLOCATOR>
190/// int my_Stack<ALLOCATOR>::top()
191/// {
192/// BSLS_ASSERT(0 != size());
193///
194/// return d_head_p->d_value;
195/// }
196///
197/// template <class ALLOCATOR>
198/// std::size_t my_Stack<ALLOCATOR>::size()
199/// {
200/// return d_size;
201/// }
202/// @endcode
203/// Finally, we test our stack by pushing and popping some elements:
204/// @code
205/// my_Stack stack;
206/// stack.push(1);
207/// stack.push(2);
208/// stack.push(3);
209/// stack.push(4);
210/// stack.push(5);
211/// assert(5 == stack.size());
212///
213/// assert(5 == stack.top());
214/// stack.pop();
215/// assert(4 == stack.top());
216/// stack.pop();
217/// assert(3 == stack.top());
218/// stack.pop();
219/// assert(2 == stack.top());
220/// stack.pop();
221/// assert(1 == stack.top());
222/// stack.pop();
223/// assert(0 == stack.size());
224/// @endcode
225/// @}
226/** @} */
227/** @} */
228
229/** @addtogroup bsl
230 * @{
231 */
232/** @addtogroup bslstl
233 * @{
234 */
235/** @addtogroup bslstl_simplepool
236 * @{
237 */
238
239#include <bslscm_version.h>
240
242#include <bslma_allocatorutil.h>
243
244#include <bslmf_movableref.h>
245
247#include <bsls_alignmentutil.h>
248#include <bsls_assert.h>
249#include <bsls_platform.h>
250
251#include <algorithm> // swap (C++03)
252#include <utility> // swap (C++17)
253
254
255namespace bslstl {
256
257 // ======================
258 // struct SimplePool_Type
259 // ======================
260
261/// For use only by `bslstl::SimplePool`. This `struct` provides a
262/// namespace for a set of types used to define the base-class of a
263/// `SimplePool`. The parameterized `ALLOCATOR` is bound to
264/// `MaxAlignedType` to ensure the allocated memory is maximally aligned.
265///
266/// See @ref bslstl_simplepool
267template <class ALLOCATOR>
269
270 /// Alias for the allocator traits rebound to allocate
271 /// `bsls::AlignmentUtil::MaxAlignedType`.
273 rebind_traits<bsls::AlignmentUtil::MaxAlignedType> AllocatorTraits;
274
275 /// Alias for the allocator type for
276 /// `bsls::AlignmentUtil::MaxAlignedType`.
277 typedef typename AllocatorTraits::allocator_type AllocatorType;
278};
279
280 // ================
281 // class SimplePool
282 // ================
283
284/// This class provides methods for creating and deleting nodes using the
285/// appropriate allocator-traits of the parameterized `ALLOCATOR`.
286/// This type is intended to be used as a private base-class for a
287/// node-based container, in order to take advantage of the
288/// empty-base-class optimization in the case where the base-class has 0
289/// size (as may the case if the parameterized `ALLOCATOR` is not a
290/// `bslma::Allocator`).
291///
292/// See @ref bslstl_simplepool
293template <class VALUE, class ALLOCATOR>
294class SimplePool : public SimplePool_Type<ALLOCATOR>::AllocatorType {
295
296 // PRIVATE TYPES
298
299 enum { k_MAX_BLOCKS_PER_CHUNK = 32 };
300
301 /// This `union` implements a link data structure with the size no
302 /// smaller than `VALUE` that stores the address of the next link.
303 /// It is used to implement the internal linked list of free memory
304 /// blocks.
305 union Block {
306
307 Block *d_next_p; // pointer to the next block
308
309 char d_size[sizeof(VALUE)]; // make a block has the size of at
310 // least `VALUE`
311
312 typename bsls::AlignmentFromType<VALUE>::Type d_alignment;
313 // ensure proper alignment
314 };
315
316 /// This `union` prepends to the beginning of each managed block of
317 /// allocated memory, implementing a singly-linked list of managed
318 /// chunks, and thereby enabling constant-time additions to the list of
319 /// chunks.
320 union Chunk {
321
322 struct {
323 Chunk *d_next_p;
324 typename Types::AllocatorTraits::size_type d_numBytes;
325 } d_info;
326
327 typename bsls::AlignmentFromType<Block>::Type d_alignment;
328 // ensure each block is correctly aligned
329
330 /// Return a pointer to the first block in this chunk.
331 Block *firstBlock()
332 { return reinterpret_cast<Block *>(this + 1); }
333 };
334
335 public:
336 // TYPES
337
338 /// Alias for the parameterized type `VALUE`.
339 typedef VALUE ValueType;
340
341 /// Alias for the allocator type for a
342 /// `bsls::AlignmentUtil::MaxAlignedType`.
344
345 /// Alias for the allocator traits for the parameterized
346 /// `ALLOCATOR`.
348
349 typedef typename AllocatorTraits::size_type size_type;
350
351 private:
352 // DATA
353 Chunk *d_chunkList_p; // linked list of "chunks" of memory
354
355 Block *d_freeList_p; // linked list of free memory blocks
356
357 int d_blocksPerChunk; // current chunk size (in blocks-per-chunk)
358
359 private:
360 // NOT IMPLEMENTED
362 SimplePool& operator=(const SimplePool&);
363 SimplePool(const SimplePool&);
364
365 private:
366 // PRIVATE MANIPULATORS
367
368 /// Allocate a chunk of memory having enough usable blocks for the
369 /// specified `numBlocks` objects of type `VALUE`, add the chunk to the
370 /// chunk list, and return the address of the chunk header.
371 Chunk *allocateChunk(std::size_t numBlocks);
372
373 /// Deallocate a chunk of memory at the specified `chunk_p` address.
374 ///
375 /// \pre The behavior is undefined unless `chunk_p` was allocate from this
376 /// pool using `allocateChunk` and not yet deallocated.
377 void deallocateChunk(Chunk *chunk_p);
378
379 /// Dynamically allocate a new chunk using the pool's underlying growth
380 /// strategy, and use the chunk to replenish the free memory list of
381 /// this pool.
382 void replenish();
383
384 public:
385 // CREATORS
386
387 /// Create a memory pool that returns blocks of contiguous memory of the
388 /// size of the parameterized `VALUE` using the specified `allocator` to
389 /// supply memory. The chunk size grows starting with at least
390 /// `sizeof(VALUE)`, doubling in size up to an implementation defined
391 /// maximum number of blocks per chunk.
392 explicit SimplePool(const ALLOCATOR& allocator);
393
394 /// Create a memory pool, adopting all outstanding memory allocations
395 /// associated with the specified `original` pool, that returns blocks
396 /// of contiguous memory of the sizeof the paramterized `VALUE` using
397 /// the allocator associated with `original`. The chunk size is set to
398 /// that of `original` and continues to double in size up to an
399 /// implementation defined maximum number of blocks per chunk.
400 ///
401 /// \note Note that `original` is left in a valid but unspecified state.
403
404 /// Destroy this pool, releasing all associated memory back to the
405 /// underlying allocator.
407
408 // MANIPULATORS
409
410 /// Adopt all outstanding memory allocations associated with the specified memory `pool`.
411 ///
412 /// \pre The behavior is undefined unless this pool
413 /// uses the same allocator as that associated with `pool`.
414 ///
415 /// \pre The behavior is undefined unless this pool is in the default-constructed
416 /// state.
418
419 /// Return a reference providing modifiable access to the rebound allocator traits for the node-type.
420 ///
421 /// \note Note that this operation
422 /// returns a base-class (`AllocatorType`) reference to this object.
424
425 /// Return the address of a block of memory of at least the size of `VALUE`.
426 ///
427 /// \note Note that the memory is *not* initialized.
428 VALUE *allocate();
429
430 /// Relinquish the memory block at the specified `address` back to this pool object for reuse.
431 ///
432 /// \pre The behavior is undefined unless `address`
433 /// is non-zero, was allocated by this pool, and has not already been
434 /// deallocated.
435 void deallocate(void *address);
436
437 /// Dynamically allocate a new chunk containing the specified
438 /// `numBlocks` number of blocks, and add the chunk to the free memory
439 /// list of this pool. The additional memory is added irrespective of
440 /// the amount of free memory when called.
441 ///
442 /// \pre The behavior is undefined unless `0 < numBlocks`.
443 void reserve(size_type numBlocks);
444
445 /// Relinquish all memory currently allocated via this pool object.
446 void release();
447
448 /// Efficiently exchange the memory blocks of this object with those of
449 /// the specified `other` object. This method provides the no-throw exception-safety guarantee.
450 ///
451 /// \pre The behavior is undefined unless
452 /// `allocator() == other.allocator()`.
453 void swap(SimplePool& other);
454
455 /// Efficiently exchange the memory blocks of this object with those of
456 /// the specified `other` object. This method provides the no-throw exception-safety guarantee.
457 ///
458 /// \pre The behavior is undefined unless
459 /// `allocator() == other.allocator()`.
461
462 /// Efficiently exchange the memory blocks and the allocator of this
463 /// object with those of the specified `other` object. This method
464 /// provides the no-throw exception-safety guarantee.
466
467 // ACCESSORS
468
469 /// Return a reference providing non-modifiable access to the rebound allocator traits for the node-type.
470 ///
471 /// \note Note that this operation
472 /// returns a base-class (`AllocatorType`) reference to this object.
473 const AllocatorType& allocator() const;
474
475 /// Return `true` if this object holds free (currently unused) blocks,
476 /// and `false` otherwise.
477 bool hasFreeBlocks() const;
478};
479
480// ============================================================================
481// TEMPLATE AND INLINE FUNCTION DEFINITIONS
482// ============================================================================
483
484// PRIVATE MANIPULATORS
485template <class VALUE, class ALLOCATOR>
488{
489 std::size_t numBytes = sizeof(Chunk) + sizeof(Block) * numBlocks;
490 const std::size_t alignment = bsls::AlignmentFromType<Chunk>::VALUE;
491
492 Chunk *chunkPtr =
493 static_cast<Chunk *>(bslma::AllocatorUtil::allocateBytes(allocator(),
494 numBytes,
495 alignment));
496
498 reinterpret_cast<bsls::Types::UintPtr>(chunkPtr) % alignment);
499
500 chunkPtr->d_info.d_next_p = d_chunkList_p;
501 chunkPtr->d_info.d_numBytes = numBytes;
502 d_chunkList_p = chunkPtr;
503
504 return chunkPtr;
505}
506
507template <class VALUE, class ALLOCATOR>
508inline void
509SimplePool<VALUE, ALLOCATOR>::deallocateChunk(Chunk *chunk_p)
510{
511 std::size_t numBytes = chunk_p->d_info.d_numBytes;
512 const std::size_t alignment = bsls::AlignmentFromType<Chunk>::VALUE;
513
514 bslma::AllocatorUtil::deallocateBytes(allocator(), chunk_p,
515 numBytes, alignment);
516}
517
518template <class VALUE, class ALLOCATOR>
519inline
520void SimplePool<VALUE, ALLOCATOR>::replenish()
521{
522 reserve(d_blocksPerChunk);
523
524 if (d_blocksPerChunk < k_MAX_BLOCKS_PER_CHUNK) {
525 d_blocksPerChunk *= 2;
526 }
527}
528
529// CREATORS
530template <class VALUE, class ALLOCATOR>
531inline
533: AllocatorType(allocator)
534, d_chunkList_p(0)
535, d_freeList_p(0)
536, d_blocksPerChunk(1)
537{
538}
539
540template <class VALUE, class ALLOCATOR>
541inline
544: AllocatorType(bslmf::MovableRefUtil::access(original).allocator())
545, d_chunkList_p(bslmf::MovableRefUtil::access(original).d_chunkList_p)
546, d_freeList_p(bslmf::MovableRefUtil::access(original).d_freeList_p)
547, d_blocksPerChunk(bslmf::MovableRefUtil::access(original).d_blocksPerChunk)
548{
549 SimplePool& lvalue = original;
550 lvalue.d_chunkList_p = 0;
551 lvalue.d_freeList_p = 0;
552 lvalue.d_blocksPerChunk = 1;
553}
554
555template <class VALUE, class ALLOCATOR>
556inline
561
562// MANIPULATORS
563template <class VALUE, class ALLOCATOR>
564inline
565void
567{
568 BSLS_ASSERT_SAFE(0 == d_chunkList_p);
569 BSLS_ASSERT_SAFE(0 == d_freeList_p);
570 BSLS_ASSERT_SAFE(allocator()
571 == bslmf::MovableRefUtil::access(pool).allocator());
572
573 SimplePool& lvalue = pool;
574 d_chunkList_p = lvalue.d_chunkList_p;
575 d_freeList_p = lvalue.d_freeList_p;
576 d_blocksPerChunk = lvalue.d_blocksPerChunk;
577
578 lvalue.d_chunkList_p = 0;
579 lvalue.d_freeList_p = 0;
580 lvalue.d_blocksPerChunk = 1;
581}
582
583template <class VALUE, class ALLOCATOR>
584inline
587{
588 return *this;
589}
590
591template <class VALUE, class ALLOCATOR>
592inline
594{
595 if (!d_freeList_p) {
596 replenish();
597 }
598 VALUE *block = reinterpret_cast<VALUE *>(d_freeList_p);
599 d_freeList_p = d_freeList_p->d_next_p;
600 return block;
601}
602
603template <class VALUE, class ALLOCATOR>
604inline
606{
607 BSLS_ASSERT_SAFE(address);
608
609 reinterpret_cast<Block *>(address)->d_next_p = d_freeList_p;
610 d_freeList_p = reinterpret_cast<Block *>(address);
611}
612
613template <class VALUE, class ALLOCATOR>
614inline
616{
617 BSLS_ASSERT_SAFE(allocator() == other.allocator());
618
619 std::swap(d_blocksPerChunk, other.d_blocksPerChunk);
620 std::swap(d_freeList_p, other.d_freeList_p);
621 std::swap(d_chunkList_p, other.d_chunkList_p);
622}
623
624template <class VALUE, class ALLOCATOR>
625inline
631
632template <class VALUE, class ALLOCATOR>
633inline
636{
637 // We don't know which operation (copy/move assignment or swap) this
638 // function is being called for, but if any of the propagation traits are
639 // true, then the allocator must support assignment, so we turn propagation
640 // on for all of them.
641 typedef bsl::allocator_traits<ALLOCATOR> AllocTraits;
643 bool,
644 AllocTraits::propagate_on_container_copy_assignment::value ||
645 AllocTraits::propagate_on_container_move_assignment::value ||
646 AllocTraits::propagate_on_container_swap::value> Propagate;
647
648 using std::swap;
649 using BloombergLP::bslma::AllocatorUtil;
650 AllocatorUtil::swap(&this->allocator(), &other.allocator(), Propagate());
651 swap(d_blocksPerChunk, other.d_blocksPerChunk);
652 swap(d_freeList_p, other.d_freeList_p);
653 swap(d_chunkList_p, other.d_chunkList_p);
654}
655
656template <class VALUE, class ALLOCATOR>
658{
659 BSLS_ASSERT(0 < numBlocks);
660
661 Block *begin = allocateChunk(numBlocks)->firstBlock();
662 Block *end = begin + numBlocks - 1; // last block, NOT past-the-end
663
664 // The last block is deliberately excluded from this loop.
665 for (Block *p = begin; p < end; ++p) {
666 p->d_next_p = p + 1;
667 }
668 end->d_next_p = d_freeList_p; // Handle the last block here
669 d_freeList_p = begin;
670}
671
672template <class VALUE, class ALLOCATOR>
674{
675 while (d_chunkList_p) {
676 Chunk *lastChunk = d_chunkList_p;
677 d_chunkList_p = d_chunkList_p->d_info.d_next_p;
678 deallocateChunk(lastChunk);
679 }
680
681 d_freeList_p = 0;
682}
683
684// ACCESSORS
685template <class VALUE, class ALLOCATOR>
686inline
689{
690 return *this;
691}
692
693template <class VALUE, class ALLOCATOR>
694inline
696{
697 return d_freeList_p;
698}
699
700} // close package namespace
701
702
703#endif
704
705// ----------------------------------------------------------------------------
706// Copyright 2019 Bloomberg Finance L.P.
707//
708// Licensed under the Apache License, Version 2.0 (the "License");
709// you may not use this file except in compliance with the License.
710// You may obtain a copy of the License at
711//
712// http://www.apache.org/licenses/LICENSE-2.0
713//
714// Unless required by applicable law or agreed to in writing, software
715// distributed under the License is distributed on an "AS IS" BASIS,
716// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
717// See the License for the specific language governing permissions and
718// limitations under the License.
719// ----------------------------- END-OF-FILE ----------------------------------
720
721/** @} */
722/** @} */
723/** @} */
Definition bslmf_movableref.h:752
Definition bslstl_simplepool.h:294
void release()
Relinquish all memory currently allocated via this pool object.
Definition bslstl_simplepool.h:673
Types::AllocatorType AllocatorType
Definition bslstl_simplepool.h:343
void adopt(bslmf::MovableRef< SimplePool > pool)
Definition bslstl_simplepool.h:566
bool hasFreeBlocks() const
Definition bslstl_simplepool.h:695
const AllocatorType & allocator() const
Definition bslstl_simplepool.h:688
void quickSwapExchangeAllocators(SimplePool &other)
Definition bslstl_simplepool.h:634
VALUE ValueType
Alias for the parameterized type VALUE.
Definition bslstl_simplepool.h:339
void deallocate(void *address)
Definition bslstl_simplepool.h:605
AllocatorType & allocator()
Definition bslstl_simplepool.h:586
AllocatorTraits::size_type size_type
Definition bslstl_simplepool.h:349
~SimplePool()
Definition bslstl_simplepool.h:557
SimplePool(const ALLOCATOR &allocator)
Definition bslstl_simplepool.h:532
void quickSwapRetainAllocators(SimplePool &other)
Definition bslstl_simplepool.h:626
void reserve(size_type numBlocks)
Definition bslstl_simplepool.h:657
void swap(SimplePool &other)
Definition bslstl_simplepool.h:615
VALUE * allocate()
Definition bslstl_simplepool.h:593
SimplePool(bslmf::MovableRef< SimplePool > original)
Definition bslstl_simplepool.h:542
Types::AllocatorTraits AllocatorTraits
Definition bslstl_simplepool.h:347
#define BSLS_ASSERT(X)
Definition bsls_assert.h:1976
#define BSLS_ASSERT_SAFE(X)
Definition bsls_assert.h:1917
#define BSLS_IDENT(str)
BSLS_IDENT() - insert string into .comment binary segment (if supported)
Definition bsls_ident.h:238
int reserve(TYPE *array, int numElements)
Definition bdlbb_blob.h:579
Definition bslstl_algorithm.h:84
Definition bslma_allocatortraits.h:1089
Definition bslmf_integralconstant.h:261
static AllocatorUtil_Traits< t_ALLOCATOR >::void_pointer allocateBytes(const t_ALLOCATOR &allocator, std::size_t nbytes, std::size_t alignment=0)
Definition bslma_allocatorutil.h:886
static void deallocateBytes(const t_ALLOCATOR &allocator, typename AllocatorUtil_Traits< t_ALLOCATOR >::void_pointer p, std::size_t nbytes, std::size_t alignment=0)
Definition bslma_allocatorutil.h:930
static t_TYPE & access(t_TYPE &ref) BSLS_KEYWORD_NOEXCEPT
Definition bslmf_movableref.h:1039
Definition bsls_alignmentfromtype.h:378
AlignmentToType< VALUE >::Type Type
Definition bsls_alignmentfromtype.h:388
std::size_t UintPtr
Definition bsls_types.h:128
Definition bslstl_simplepool.h:268
AllocatorTraits::allocator_type AllocatorType
Definition bslstl_simplepool.h:277
bsl::allocator_traits< ALLOCATOR >::template rebind_traits< bsls::AlignmentUtil::MaxAlignedType > AllocatorTraits
Definition bslstl_simplepool.h:273