BDE 4.39.x Production Release
Loading...
Searching...
No Matches
bslma_sharedptrrep.h
Go to the documentation of this file.
1/// @file bslma_sharedptrrep.h
2///
3/// The content of this file has been pre-processed for Doxygen.
4///
5
6
7// bslma_sharedptrrep.h -*-C++-*-
8#ifndef INCLUDED_BSLMA_SHAREDPTRREP
9#define INCLUDED_BSLMA_SHAREDPTRREP
10
11#include <bsls_ident.h>
12BSLS_IDENT("$Id$ $CSID$")
13
14/// @defgroup bslma_sharedptrrep bslma_sharedptrrep
15/// @brief Provide an abstract class for a shared object manager.
16/// @addtogroup bsl
17/// @{
18/// @addtogroup bslma
19/// @{
20/// @addtogroup bslma_sharedptrrep
21/// @{
22///
23/// <h1> Outline </h1>
24/// * <a href="#bslma_sharedptrrep-purpose"> Purpose</a>
25/// * <a href="#bslma_sharedptrrep-classes"> Classes </a>
26/// * <a href="#bslma_sharedptrrep-description"> Description </a>
27/// * <a href="#bslma_sharedptrrep-shared-and-weak-references"> Shared and Weak References </a>
28/// * <a href="#bslma_sharedptrrep-thread-safety"> Thread Safety </a>
29/// * <a href="#bslma_sharedptrrep-disposeobject-and-disposerep"> disposeObject and disposeRep </a>
30/// * <a href="#bslma_sharedptrrep-usage"> Usage </a>
31///
32/// # Purpose {#bslma_sharedptrrep-purpose}
33/// Provide an abstract class for a shared object manager.
34///
35/// # Classes {#bslma_sharedptrrep-classes}
36///
37/// - bslma::SharedPtrRep : shared pointer representation abstract class
38///
39/// @see bslstl_sharedptr, bslma_sharedptrrep_inplace,
40/// bslma_sharedptrrep_outofplace
41///
42/// # Description {#bslma_sharedptrrep-description}
43/// This component provides a partially implemented abstract class,
44/// `bslma::SharedPtrRep`, for managing the lifetime of a shared object.
45/// `bslma::SharedPtrRep` provides a count of both shared and weak references to
46/// a shared object (described in more detail in the next section). In
47/// addition, `bslma::SharedPtrRep` provides protocol methods that allows a
48/// concrete implementation to specify what action should be taken when these
49/// reference counts reach zero.
50///
51/// ## Shared and Weak References {#bslma_sharedptrrep-shared-and-weak-references}
52///
53///
54/// There are two types of references to shared objects:
55///
56/// 1) A shared reference allows users to share the ownership of an object and
57/// control its lifetime. A shared object is destroyed only when the last
58/// shared reference to it is released. The function `acquireRef` should be
59/// called when a new shared reference is created and `releaseRef` should be
60/// called when a share reference is removed.
61///
62/// 2) A weak reference provides users conditional access to an object without
63/// sharing its ownership (or affecting its lifetime). A shared object can be
64/// destroyed even if there are weak references to it. The function
65/// `acquireWeakRef` should be called when a new weak reference is created and
66/// `releaseWeakRef` should be called when a weak reference is removed.
67///
68/// ## Thread Safety {#bslma_sharedptrrep-thread-safety}
69///
70///
71/// `bslma::SharedPtrRep` is thread-safe provided that `disposeObject` and
72/// `disposeRep` are not called explicitly, meaning that all non-creator
73/// operations other than `disposeObject` and `disposeRep` on a given instance
74/// can be safely invoked simultaneously from multiple threads (`disposeObject`
75/// and `disposeRep` are meant to be implemented by types inheriting
76/// `bslma::SharedPtrRep`, and invoked only by `releaseRef` and
77/// `releaseWeakRef`). Note that there is no thread safety guarantees for
78/// operations on the managed object.
79///
80/// ## disposeObject and disposeRep {#bslma_sharedptrrep-disposeobject-and-disposerep}
81///
82///
83/// `disposeObject` is meant to act as the destructor of the managed object and
84/// each derived class must override this method to perform an action that
85/// releases the shared object from management, such as deleting the managed
86/// object. `disposeObject` will be called when the last shared reference to
87/// the object has been released using `releaseRef`.
88///
89/// `disposeRep` is meant to act as the destructor of `bslma::SharedPtrRep`.
90/// The destructor of `bslma::SharedPtrRep` is declared as private and cannot be
91/// called. The derived class must override `disposeRep` to perform an action
92/// such as deallocating the memory of the instance of the derived class.
93/// `disposeRep` will be called when both the last shared reference and the last
94/// weak reference to the object has been released using `releaseRef` or
95/// `releaseWeakRef`.
96///
97/// ## Usage {#bslma_sharedptrrep-usage}
98///
99///
100/// The following example demonstrates how to implement a shared
101/// `bdlt::Datetime` using `bslma::SharedPtrRep`. In this example, the
102/// implementation will store an object of `bdlt::Datetime` in-place. First, we
103/// define an implementation of `bslma::SharedPtrRep`:
104/// @code
105/// class MySharedDatetimeRepImpl : public bslma::SharedPtrRep {
106/// // Implementation of 'bslma::SharedPtrRep' for an in-place
107/// // 'bdlt::Datetime' object.
108///
109/// // DATA
110/// bslma::Allocator *d_allocator_p; // memory allocator (held, not owned)
111/// bdlt::Datetime d_instance; // in-place object
112///
113/// private:
114/// // NOT IMPLEMENTED
115/// MySharedDatetimeRepImpl(const MySharedDatetimeRepImpl&);
116/// MySharedDatetimeRepImpl& operator=(const MySharedDatetimeRepImpl&);
117///
118/// public:
119/// // CREATORS
120/// MySharedDatetimeRepImpl(bslma::Allocator *basicAllocator,
121/// int year,
122/// int month,
123/// int day);
124/// // Create a shared representation of a 'bdlt::Datetime' object
125/// // having the specified 'year', 'month' and 'day' using the
126/// // specified 'basicAllocator' to supply memory.
127///
128/// // MANIPULATORS
129/// virtual void disposeRep();
130/// // Dispose of this 'MySharedDatetimeRepImpl' object.
131///
132/// virtual void disposeObject();
133/// // Dispose of the managed 'bdlt::Datetime' object.
134///
135/// // ACCESSORS
136/// bdlt::Datetime *ptr();
137/// // Return the address of the modifiable managed 'bdlt::Datetime'
138/// // object.
139///
140/// virtual void *originalPtr() const;
141/// // Return the address of the modifiable managed 'bdlt::Datetime'
142/// // object.
143/// };
144/// @endcode
145/// Next, we define the implementation:
146/// @code
147/// // CREATORS
148/// MySharedDatetimeRepImpl::MySharedDatetimeRepImpl(
149/// bslma::Allocator *basicAllocator,
150/// int year,
151/// int month,
152/// int day)
153/// : d_allocator_p(basicAllocator)
154/// , d_instance(year, month, day)
155/// {
156/// }
157///
158/// void MySharedDatetimeRepImpl::disposeRep()
159/// {
160/// d_allocator_p->deallocate(this);
161/// }
162///
163/// void MySharedDatetimeRepImpl::disposeObject()
164/// {
165/// d_instance.~bdlt::Datetime();
166/// }
167///
168/// bdlt::Datetime *MySharedDatetimeRepImpl::ptr()
169/// {
170/// return &d_instance;
171/// }
172///
173/// void *MySharedDatetimeRepImpl::originalPtr() const {
174/// return bslma::PointerUtil::voidify(&d_instance);
175/// }
176/// @endcode
177/// Next, we implement a shared `bdlt::Datetime` class.
178/// @code
179/// class MySharedDatetimePtr {
180/// // This class provides a reference counted managed pointer to support
181/// // shared ownership of a 'bdlt::Datetime' object.
182///
183/// bdlt::Datetime *d_ptr_p; // pointer to the managed object
184/// bslma::SharedPtrRep *d_rep_p; // pointer to the representation object
185///
186/// private:
187/// // NOT IMPLEMENTED
188/// MySharedDatetimePtr& operator=(const MySharedDatetimePtr&);
189///
190/// public:
191/// // CREATORS
192/// MySharedDatetimePtr();
193/// // Create an empty shared datetime.
194///
195/// MySharedDatetimePtr(bdlt::Datetime* ptr, bslma::SharedPtrRep* rep);
196/// // Create a shared datetime that adopts ownership of the specified
197/// // 'ptr' and the specified 'rep'.
198///
199/// MySharedDatetimePtr(const MySharedDatetimePtr& original);
200/// // Create a shared datetime that refers to the same object managed
201/// // by the specified 'original'
202///
203/// ~MySharedDatetimePtr();
204/// // Destroy this shared datetime and release the reference to the
205/// // 'bdlt::Datetime' object to which it might be referring. If this
206/// // is the last shared reference, deleted the managed object.
207///
208/// // MANIPULATORS
209/// void createInplace(bslma::Allocator *basicAllocator,
210/// int year,
211/// int month,
212/// int day);
213/// // Create a new 'MySharedDatetimeRepImpl', using the specified
214/// // 'basicAllocator' to supply memory, using the specified 'year',
215/// // 'month' and 'day' to initialize the 'bdlt::Datetime' within the
216/// // newly created 'MySharedDatetimeRepImpl', and make this
217/// // object refer to the newly created 'bdlt::Datetime' object.
218///
219/// // ACCESSORS
220/// bdlt::Datetime& operator*() const;
221/// // Return a reference to the modifiable 'bdlt::Datetime' to which
222/// // this object refers.
223///
224/// bdlt::Datetime *operator->() const;
225/// // Return the address of the modifiable 'bdlt::Datetime' to which
226/// // this object refers.
227///
228/// bdlt::Datetime *ptr() const;
229/// // Return the address of the modifiable 'bdlt::Datetime' to which
230/// // this object refers.
231/// };
232/// @endcode
233/// Finally, we implement `MySharedDatetimePtr`:
234/// @code
235/// MySharedDatetimePtr::MySharedDatetimePtr()
236/// : d_ptr_p(0)
237/// , d_rep_p(0)
238/// {
239/// }
240///
241/// MySharedDatetimePtr::MySharedDatetimePtr(bdlt::Datetime *ptr,
242/// bslma::SharedPtrRep *rep)
243/// : d_ptr_p(ptr)
244/// , d_rep_p(rep)
245/// {
246/// }
247///
248/// MySharedDatetimePtr::MySharedDatetimePtr(
249/// const MySharedDatetimePtr& original)
250/// : d_ptr_p(original.d_ptr_p)
251/// , d_rep_p(original.d_rep_p)
252/// {
253/// if (d_ptr_p) {
254/// d_rep_p->acquireRef();
255/// } else {
256/// d_rep_p = 0;
257/// }
258/// }
259///
260/// MySharedDatetimePtr::~MySharedDatetimePtr()
261/// {
262/// if (d_rep_p) {
263/// d_rep_p->releaseRef();
264/// }
265/// }
266///
267/// void MySharedDatetimePtr::createInplace(bslma::Allocator *basicAllocator,
268/// int year,
269/// int month,
270/// int day)
271/// {
272/// basicAllocator = bslma::Default::allocator(basicAllocator);
273/// MySharedDatetimeRepImpl *rep = new (*basicAllocator)
274/// MySharedDatetimeRepImpl(basicAllocator,
275/// year,
276/// month,
277/// day);
278/// MySharedDatetimePtr temp(rep->ptr(), rep);
279/// bsl::swap(d_ptr_p, temp.d_ptr_p);
280/// bsl::swap(d_rep_p, temp.d_rep_p);
281/// }
282///
283/// bdlt::Datetime& MySharedDatetimePtr::operator*() const
284/// {
285/// return *d_ptr_p;
286/// }
287///
288/// bdlt::Datetime *MySharedDatetimePtr::operator->() const
289/// {
290/// return d_ptr_p;
291/// }
292///
293/// bdlt::Datetime *MySharedDatetimePtr::ptr() const
294/// {
295/// return d_ptr_p;
296/// }
297/// @endcode
298/// @}
299/** @} */
300/** @} */
301
302/** @addtogroup bsl
303 * @{
304 */
305/** @addtogroup bslma
306 * @{
307 */
308/** @addtogroup bslma_sharedptrrep
309 * @{
310 */
311
312#include <bslscm_version.h>
313
314#include <bsls_assert.h>
315#include <bsls_atomic.h>
316
317#include <typeinfo>
318
319
320namespace bslma {
321
322 // ==================
323 // class SharedPtrRep
324 // ==================
325
326/// This class provides a partially implemented shared pointer
327/// representation ("letter") protocol. The class provides two counters for
328/// storing the number of shared and weak references, and functions to
329/// increment and decrement these counters. In addition, this class
330/// provides protocol methods that allow concrete implementations to specify
331/// what action should be taken when these counts reach zero. The function
332/// `disposeRep` is responsible for destroying this object, it is called
333/// when the reference count to this object reaches zero. Thus, the
334/// destructor of this object is declared as protected and should never be
335/// invoked.
336///
337/// See @ref bslma_sharedptrrep
339
340 // DATA
341 bsls::AtomicInt d_adjustedSharedCount;
342 // Counter storing a value that allows us to
343 // calculate the number of shared references.
344 // The numerical value of 'd_adjustedSharedCount'
345 // is: 2 * number of shared references, plus 1 if
346 // any weak references were *ever* created.
347
348 bsls::AtomicInt d_adjustedWeakCount;
349 // Counter storing a value that allows us to
350 // calculate the number of weak references. The
351 // numerical value of 'd_adjustedWeakCount' is:
352 // 2 * number of weak references, plus 1 if there
353 // are any *outstanding* shared references.
354
355 private:
356 // NOT IMPLEMENTED
357 SharedPtrRep(const SharedPtrRep&); // = delete
358 SharedPtrRep& operator=(const SharedPtrRep&); // = delete
359
360 // PRIVATE ACCESSORS
361
362 /// Do nothing.
363 /// \note Note that this function is added to avoid including a
364 /// (redundant) vtable into every translation unit that includes this
365 /// type. Although we expect that these redundant vtables, identified
366 /// by the `-Wweak-vtables` warning of the clang compiler (version 4.0
367 /// and higher), will be consolidated by the linker, this workaround
368 /// avoids the space being used in the generated object files, which may
369 /// be important for very heavily used types like this one.
370 /// Implementing a virtual function out-of-line enables the compiler to
371 /// use this component translation unit as a "home" for the single
372 /// shared copy of the vtable.
373 virtual void vtableDummy() const;
374
375 protected:
376 // PROTECTED CREATORS
377
378 /// Destroy this representation object.
379 /// \note Note that this destructor is
380 /// not intended to be invoked polymorphically, and is marked `virtual`
381 /// only to silence frequent warnings on popular compilers.
382 virtual ~SharedPtrRep();
383
384 public:
385 // CLASS METHODS
386
387 /// Release the shared reference to an object held by the `SharedPtrRep`
388 /// object that is pointed to be by specified `rep`.
389 ///
390 /// \pre The behavior is undefined unless `rep` points to an object whose complete type
391 /// publicly and unambiguously derives from `SharedPtrRep`.
392 ///
393 /// \note Note that the first argument is ignored. Also note that this function serves
394 /// as the `ManagedPtr` deleter when converting a `bsl::shared_ptr` to a
395 /// `bslma::ManagedPtr`.
396 static void managedPtrDeleter(void *, void *rep);
397
398 /// This function has no effect.
399 /// \pre The behavior is undefined unless `rep` is null.
400 ///
401 /// \note Note that this function serves as the managed ptr deleter
402 /// when converting an empty or null `bsl::shared_ptr` to a
403 /// `bslma::ManagedPtr`.
404 static void managedPtrEmptyDeleter(void *, void *rep);
405
406 // CREATORS
407
408 /// Create a `SharedPtrRep` object having one shared reference and no
409 /// weak references.
410 SharedPtrRep();
411
412 // PURE VIRTUAL FUNCTIONS
413
414 /// Dispose of the shared object referred to by this representation.
415 /// This method is automatically invoked by `releaseRef` when the number
416 /// of shared references reaches zero and should not be explicitly invoked otherwise.
417 ///
418 /// \note Note that this virtual `disposeObject` method
419 /// effectively serves as the shared object's destructor. Also note
420 /// that derived classes must override this method to perform the
421 /// appropriate action such as deleting the shared object.
422 virtual void disposeObject() = 0;
423
424 /// Dispose of this representation object. This method is automatically
425 /// invoked by `releaseRef` and `releaseWeakRef` when the number of weak
426 /// references and the number of shared references both reach zero and
427 /// should not be explicitly invoked otherwise.
428 ///
429 /// \pre The behavior is undefined unless `disposeObject` has already been called for this representation.
430 ///
431 /// \note Note that this virtual `disposeRep` method
432 /// effectively serves as the representation object's destructor. Also
433 /// note that derived classes must override this method to perform
434 /// appropriate action such as deleting this representation, or
435 /// returning it to an object pool.
436 virtual void disposeRep() = 0;
437
438 /// Return a pointer to the deleter stored by the derived representation
439 /// (if any) if the deleter has the same type as that described by the specified `type`, and a null pointer otherwise.
440 ///
441 /// \note Note that while
442 /// this methods appears to be a simple accessor, it is declared as non-
443 /// `const` qualified to support representations storing the deleter
444 /// directly as a data member.
445 virtual void *getDeleter(const std::type_info& type) = 0;
446
447 /// Return the (untyped) address of the modifiable shared object
448 /// referred to by this representation.
449 virtual void *originalPtr() const = 0;
450
451 // MANIPULATORS
452
453 /// Atomically acquire a shared reference to the shared object referred to by this representation.
454 ///
455 /// \pre The behavior is undefined unless
456 /// `0 < numReferences()`.
457 void acquireRef();
458
459 /// Atomically acquire a weak reference to the shared object referred to by this representation.
460 ///
461 /// \pre The behavior is undefined unless
462 /// `0 < numWeakReferences() || 0 < numReferences()`.
464
465#ifndef BDE_OMIT_INTERNAL_DEPRECATED
466 /// Atomically increment the number of shared references to the shared
467 /// object referred to by this representation by the optionally specified `incrementAmount`.
468 ///
469 /// \pre The behavior is undefined unless
470 /// `0 < incrementAmount` and `0 < numReferences()`.
471 ///
472 /// DEPRECATED: Use `acquireRef` instead.
473 void incrementRefs(int incrementAmount = 1);
474#endif // BDE_OMIT_INTERNAL_DEPRECATED
475
476 /// Atomically release a shared reference to the shared object referred
477 /// to by this representation, disposing of the shared object if all the
478 /// shared references to that object are released, and disposing of this
479 /// representation if all (shared and weak) references to that object are released.
480 ///
481 /// \pre The behavior is undefined unless
482 /// `0 < numReferences()`.
484
485 /// Atomically release a weak reference to the shared object referred to
486 /// by this representation, disposing of this representation if all
487 /// (shared and weak) references to the shared object are released.
488 ///
489 /// \pre The behavior is undefined unless `0 < numWeakReferences()`.
490 void releaseWeakRef();
491
492 /// Reset the number of shared references and the number of weak
493 /// references stored by this representation to the specified
494 /// `numSharedReferences` and `numWeakReferences` respectively. This
495 /// function is *not* thread-safe and users must ensure that they
496 /// serialize access to the `SharedPtrRep` object when calling this function.
497 ///
498 /// \note Note that this function updates the counts, but does not
499 /// dispose of the representation or the object irrespective of the
500 /// values of `numSharedReferences` and `numWeakReferences`.
501 void resetCountsRaw(int numSharedReferences, int numWeakReferences);
502
503 /// Atomically acquire a shared reference to the shared object referred
504 /// to by this representation, if the number of shared references is
505 /// greater than 0, and do nothing otherwise. Return `true` if the
506 /// acquire succeeds, and `false` otherwise.
507 ///
508 /// \pre The behavior is undefined unless `0 < numWeakReferences() || 0 < numReferences()`.
510
511 // ACCESSORS
512
513 /// Return `true` if there is only one shared reference and no weak
514 /// references to the object referred to by this representation, and
515 /// `false` otherwise.
516 bool hasUniqueOwner() const;
517
518 /// Return a "snapshot" of the current number of shared references to
519 /// the shared object referred to by this representation object.
520 int numReferences() const;
521
522 /// Return a "snapshot" of the current number of weak references to the
523 /// shared object referred to by this representation object.
524 int numWeakReferences() const;
525
526};
527
528// ============================================================================
529// INLINE DEFINITIONS
530// ============================================================================
531
532 // ------------------
533 // class SharedPtrRep
534 // ------------------
535
536// PROTECTED CREATORS
537inline
541
542// CLASS METHODS
543inline
544void SharedPtrRep::managedPtrDeleter(void *, void *rep)
545{
546 BSLS_ASSERT_SAFE(rep);
547
548 static_cast<SharedPtrRep *>(rep)->releaseRef();
549}
550
551inline
553{
554 BSLS_ASSERT_SAFE(!rep);
555 (void)rep; // Silence unused argument warning in non-SAFE builds.
556}
557
558// CREATORS
559inline
561: d_adjustedSharedCount(2) // minimum consistency: relaxed
562, d_adjustedWeakCount(1) // minimum consistency: relaxed
563{
564}
565
566// MANIPULATORS
567inline
569{
571
572 d_adjustedSharedCount.addRelaxed(2); // minimum consistency: relaxed
573}
574
575#ifndef BDE_OMIT_INTERNAL_DEPRECATED
576inline
577void SharedPtrRep::incrementRefs(int incrementAmount)
578{
579 BSLS_ASSERT_SAFE(0 < incrementAmount);
581
582 d_adjustedSharedCount.addRelaxed(incrementAmount * 2);
583 // minimum consistency: relaxed
584}
585#endif // BDE_OMIT_INTERNAL_DEPRECATED
586
587inline
589{
591
592 const int weakCount = d_adjustedWeakCount.add(-2);
593 // release consistency: acquire/release
594 if (0 == weakCount) {
595 disposeRep();
596 }
597}
598
599// ACCESSORS
600inline
602{
603 const int sharedCount = d_adjustedSharedCount;
604 // release consistency: acquire
605 return 2 == sharedCount
606 || (3 == sharedCount
607 && 1 == d_adjustedWeakCount); // release consistency: acquire
608}
609
610inline
612{
613 const int sharedCount = d_adjustedSharedCount.loadRelaxed();
614 // minimum consistency: relaxed
615 return sharedCount / 2;
616}
617
618inline
620{
621 const int weakCount = d_adjustedWeakCount.loadRelaxed();
622 // minimum consistency: relaxed
623 return weakCount / 2;
624}
625
626} // close package namespace
627
628
629#endif
630
631// ----------------------------------------------------------------------------
632// Copyright 2013 Bloomberg Finance L.P.
633//
634// Licensed under the Apache License, Version 2.0 (the "License");
635// you may not use this file except in compliance with the License.
636// You may obtain a copy of the License at
637//
638// http://www.apache.org/licenses/LICENSE-2.0
639//
640// Unless required by applicable law or agreed to in writing, software
641// distributed under the License is distributed on an "AS IS" BASIS,
642// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
643// See the License for the specific language governing permissions and
644// limitations under the License.
645// ----------------------------- END-OF-FILE ----------------------------------
646
647/** @} */
648/** @} */
649/** @} */
Definition bslma_sharedptrrep.h:338
virtual void * getDeleter(const std::type_info &type)=0
virtual void * originalPtr() const =0
void resetCountsRaw(int numSharedReferences, int numWeakReferences)
void releaseWeakRef()
Definition bslma_sharedptrrep.h:588
SharedPtrRep()
Definition bslma_sharedptrrep.h:560
int numWeakReferences() const
Definition bslma_sharedptrrep.h:619
bool hasUniqueOwner() const
Definition bslma_sharedptrrep.h:601
virtual ~SharedPtrRep()
Definition bslma_sharedptrrep.h:538
virtual void disposeObject()=0
static void managedPtrEmptyDeleter(void *, void *rep)
Definition bslma_sharedptrrep.h:552
void incrementRefs(int incrementAmount=1)
Definition bslma_sharedptrrep.h:577
virtual void disposeRep()=0
static void managedPtrDeleter(void *, void *rep)
Definition bslma_sharedptrrep.h:544
int numReferences() const
Definition bslma_sharedptrrep.h:611
void acquireRef()
Definition bslma_sharedptrrep.h:568
Definition bsls_atomic.h:744
int addRelaxed(int value)
Definition bsls_atomic.h:1669
int loadRelaxed() const
Definition bsls_atomic.h:1759
int add(int value)
Definition bsls_atomic.h:1657
#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
Definition baljsn_encoder_testtypes.h:76