72#ifndef _util_ref_ref_h
73#define _util_ref_ref_h
79#include <util/misc/assert.h>
82#include <mpqc_config.h>
86#ifndef REF_CHECK_STACK
87# define REF_CHECK_STACK 0
92#ifndef REF_CHECK_MAX_NREF
93# define REF_CHECK_MAX_NREF 0
95#ifndef REF_CHECK_MIN_NREF
96# define REF_CHECK_MIN_NREF 0
101#ifndef REF_CHECK_STACK
102#define REF_CHECK_STACK 0
105#ifndef REF_CHECK_STACK
106#define REF_CHECK_STACK 0
114#ifndef REF_CHECK_MAX_NREF
115#define REF_CHECK_MAX_NREF 1
118#ifndef REF_CHECK_MIN_NREF
119#define REF_CHECK_MIN_NREF 1
123#if HAVE_STHREAD || HAVE_CREATETHREAD || HAVE_PTHREAD
124#define REF_USE_LOCKS 1
127#warning "REF_USE_LOCKS not defined"
130#ifndef REF_ALWAYS_USE_LOCKS
131#define REF_ALWAYS_USE_LOCKS 1
137extern "C" void * sbrk(ssize_t);
139#define DO_REF_CHECK_STACK(p) (((void*) (p) > sbrk(0)) && (p)->managed())
141#define DO_REF_CHECK_STACK(p) (0)
145#define DO_REF_UNMANAGE(p) ((p)->unmanage())
147#define DO_REF_UNMANAGE(p)
151#define __REF_LOCK__(p) p->lock_ptr()
152#define __REF_UNLOCK__(p) p->unlock_ptr()
153#if REF_ALWAYS_USE_LOCKS
154#define __REF_INITLOCK__() use_locks(true)
156#define __REF_INITLOCK__() ref_lock_ = 0xff
159#define __REF_LOCK__(p)
160#define __REF_UNLOCK__(p)
161#define __REF_INITLOCK__()
166typedef unsigned long refcount_t;
195# define REF_MAX_NREF (UINT_MAX - 1)
196# define REF_MANAGED_CODE UINT_MAX
198# define REF_MAX_NREF UINT_MAX
200 unsigned int _reference_count_;
202 unsigned char ref_lock_;
205 void error(
const char*)
const;
206 void too_many_refs()
const;
207 void not_enough_refs()
const;
252 size_t identifier()
const {
return reinterpret_cast<const size_t>(
this); }
267 return _reference_count_;
276# if REF_CHECK_MAX_NREF
277 if (_reference_count_ >= REF_MAX_NREF) too_many_refs();
280 refcount_t r = _reference_count_;
281 __REF_UNLOCK__(
this);
291# if REF_CHECK_MIN_NREF
292 if (_reference_count_ == 0) not_enough_refs();
295 refcount_t r = _reference_count_;
296 __REF_UNLOCK__(
this);
302 return _reference_count_ != REF_MANAGED_CODE;
310 _reference_count_ = REF_MANAGED_CODE;
314 int managed() const { return 1; }
324 void warn (
const char * msg)
const;
333 void ref_info(std::ostream& os)
const;
334 void check_pointer()
const;
363 typedef T element_type;
417 operator T*()
const {
return p; }
423 bool null()
const {
return p == 0; }
424 bool operator!()
const {
436 if(p == 0 && a.
pointer() == 0){
440 else if((p != 0 && a.
pointer() == 0) || (p == 0 && a.
pointer() != 0)){
445 return p->identifier() == a->identifier();
449 template <
class A>
int operator>=(
const Ref<A>&a)
const
452 if(p == 0 && a.
pointer() == 0){
456 else if((p != 0 && a.
pointer() == 0)){
460 else if((p == 0 && a.
pointer() != 0)){
465 return p->identifier() >= a->identifier();
469 template <
class A>
int operator<=(
const Ref<A>&a)
const
472 if(p == 0 && a.pointer() == 0){
476 else if((p != 0 && a.pointer() == 0)){
480 else if((p == 0 && a.pointer() != 0)){
485 return p->identifier() <= a->identifier();
489 template <
class A>
int operator>(
const Ref<A>&a)
const
492 if(p == 0 && a.pointer() == 0){
496 else if((p != 0 && a.pointer() == 0)){
500 else if((p == 0 && a.pointer() != 0)){
505 return p->identifier() > a->identifier();
509 template <
class A>
int operator<(
const Ref<A>&a)
const
512 if(p == 0 && a.pointer() == 0){
516 else if((p != 0 && a.pointer() == 0)){
520 else if((p == 0 && a.pointer() != 0)){
525 return p->identifier() < a->identifier();
529 template <
class A>
int operator!=(
const Ref<A>&a)
const
532 if(p == 0 && a.pointer() == 0){
536 else if((p != 0 && a.pointer() == 0) || (p == 0 && a.pointer() != 0)){
541 return p->identifier() != a->identifier();
547 return (p->identifier() == a->identifier())?0:(((p->identifier() < a->identifier())?-1:1));
553 int ref = dereference(p);
601 T* cr =
dynamic_cast<T*
>(a);
603 else if (a && a->nreference() <= 0)
delete a;
616 if (DO_REF_CHECK_STACK(cr)) {
628 if (p && p->nreference() <= 0) {
648operator<<(std::ostream& os,
const Ref<T>& r) {
658template <
typename T,
typename EqualTo = std::equal_to<T> >
660 bool operator()(
const Ref<T>& obj1,
const Ref<T>& obj2) {
661 EqualTo equal_functor;
662 return equal_functor(*obj1,*obj2);
Provides a few utility routines common to all Ref template instantiations.
Definition ref.h:321
void warn_skip_stack_delete() const
Called when the deletion of stack data is skipped.
void require_nonnull() const
Requires that a nonnull reference is held.
virtual RefCount * parentpointer() const =0
Returns the DescribedClass pointer for the contained object.
void warn(const char *msg) const
Print a warning message.
void warn_ref_to_stack() const
Called when stack data is referenced.
void warn_bad_ref_count() const
Called when the reference count is corrupted.
void ref_info(RefCount *p, std::ostream &os) const
Print information about the reference.
The base class for all reference counted objects.
Definition ref.h:192
refcount_t reference()
Increment the reference count and return the new count.
Definition ref.h:271
int unlock_ptr() const
Unlock this object.
int lock_ptr() const
Lock this object.
refcount_t nreference() const
Return the reference count.
Definition ref.h:263
int managed() const
Return 1 if the object is managed. Otherwise return 0.
Definition ref.h:314
size_t identifier() const
Return the unique identifier for this object that can be compared for different objects of different ...
Definition ref.h:252
refcount_t dereference()
Decrement the reference count and return the new count.
Definition ref.h:286
void use_locks(bool inVal)
start and stop using locks on this object
A template class that maintains references counts.
Definition ref.h:361
T & operator*() const
Returns a C++ reference to the reference counted object.
Definition ref.h:420
Ref< T > & operator<<(const RefBase &a)
Assignment to the object that a references using dynamic_cast.
Definition ref.h:588
void ref_info(std::ostream &os) const
Print information about the reference to os.
Definition ref.h:633
Ref()
Create a reference to a null object.
Definition ref.h:368
void assign_pointer(T *cr)
Assignment to cr.
Definition ref.h:613
T * pointer() const
Returns a pointer the reference counted object.
Definition ref.h:413
bool nonnull() const
Return !null().
Definition ref.h:641
RefCount * parentpointer() const
Implements the parentpointer pure virtual in the base class.
Definition ref.h:415
Ref(const Ref< T > &a)
Create a reference to the object referred to by a.
Definition ref.h:378
Ref(T *a)
Create a reference to the object a.
Definition ref.h:370
Ref< T > & operator=(const Ref< T > &c)
Assignment to c.
Definition ref.h:560
T * operator->() const
Returns the reference counted object.
Definition ref.h:411
void clear()
Refer to the null object.
Definition ref.h:550
void warn(const char *s) const
Print a warning concerning the reference.
Definition ref.h:638
void check_pointer() const
Check the validity of the pointer.
Definition ref.h:626
~Ref()
Create a reference to the object a.
Definition ref.h:406
int compare(const Ref< T > &a) const
Compare two objects returning -1, 0, or 1.
Definition ref.h:546
Ref< T > & operator=(T *cr)
Assignment to cr.
Definition ref.h:607
Ref(const Ref< A > &a)
Create a reference to the object referred to by a.
Definition ref.h:386
bool null() const
Return true if this is a reference to a null object.
Definition ref.h:423
int operator==(const Ref< A > &a) const
Ordering and equivalence operators are determined by the identifier if both pointers are not null.
Definition ref.h:433
std::vector< unsigned int > operator<<(const GaussianBasisSet &B, const GaussianBasisSet &A)
computes a map from basis functions in A to the equivalent basis functions in B.
Contains all MPQC code up to version 3.
Definition mpqcin.h:14
this functor can be used as a binary predicate for standard algorithms.
Definition ref.h:659