cartobase 6.0.6
sharedptr.h
Go to the documentation of this file.
1/* This software and supporting documentation are distributed by
2 * Institut Federatif de Recherche 49
3 * CEA/NeuroSpin, Batiment 145,
4 * 91191 Gif-sur-Yvette cedex
5 * France
6 *
7 * This software is governed by the CeCILL-B license under
8 * French law and abiding by the rules of distribution of free software.
9 * You can use, modify and/or redistribute the software under the
10 * terms of the CeCILL-B license as circulated by CEA, CNRS
11 * and INRIA at the following URL "http://www.cecill.info".
12 *
13 * As a counterpart to the access to the source code and rights to copy,
14 * modify and redistribute granted by the license, users are provided only
15 * with a limited warranty and the software's author, the holder of the
16 * economic rights, and the successive licensors have only limited
17 * liability.
18 *
19 * In this respect, the user's attention is drawn to the risks associated
20 * with loading, using, modifying and/or developing or reproducing the
21 * software by the user in light of its specific status of free software,
22 * that may mean that it is complicated to manipulate, and that also
23 * therefore means that it is reserved for developers and experienced
24 * professionals having in-depth computer knowledge. Users are therefore
25 * encouraged to load and test the software's suitability as regards their
26 * requirements in conditions enabling the security of their systems and/or
27 * data to be ensured and, more generally, to use and operate it in the
28 * same conditions as regards security.
29 *
30 * The fact that you are presently reading this means that you have had
31 * knowledge of the CeCILL-B license and that you accept its terms.
32 */
33
34#ifndef CARTOBASE_SMART_SHAREDPTR_H
35#define CARTOBASE_SMART_SHAREDPTR_H
36
39
40namespace carto
41{
42
47 class SharedObject : public virtual WeakObject, public virtual RCObject
48 {
49 public:
53 virtual ~SharedObject();
54
55 SharedObject & operator = ( const SharedObject & ) { return *this; }
56
68 bool tryDelete();
69
70 protected:
76
77 private:
78 template <typename T> friend class weak_shared_ptr;
79 template <typename T> friend class shared_ptr;
80 friend class rc_ptr_trick;
81
82 mutable RCObject::RefCounterType weak_count;
83 };
84
85
93 template <typename T>
94 class weak_shared_ptr : public rc_ptr<T>, public weak_ptr<T>
95 {
96 public:
97 explicit weak_shared_ptr( T* x = 0, bool externalowner = false );
102
103 T* get() const { return weak_ptr<T>::get(); }
104
105 bool operator == ( const T* x ) const
106 { return get() == x; }
107 bool operator == ( const weak_shared_ptr<T> & x ) const
108 { return weak_ptr<T>::operator == (x); }
109 bool operator == ( const rc_ptr<T> & x ) const
110 { return get() == x.get(); }
111 bool operator == ( const weak_ptr<T> & x ) const
112 { return get() == x.get(); }
113 bool operator != ( const T* x ) const
114 { return get() != x; }
115 bool operator != ( const weak_shared_ptr<T> & x ) const
116 { return weak_ptr<T>::operator != (x); }
117 bool operator != ( const rc_ptr<T> & x ) const
118 { return get() != x.get(); }
119 bool operator != ( const weak_ptr<T> & x ) const
120 { return get() != x.get(); }
121 bool operator < ( const weak_shared_ptr<T> & x ) const
122 { return weak_ptr<T>::operator < (x); }
123 bool operator < ( const rc_ptr<T> & x ) const
124 { return get() < x.get(); }
125 bool operator < ( const weak_ptr<T> & x ) const
126 { return get() < x.get(); }
127 T& operator * () const
128 { return weak_ptr<T>::operator * (); }
129 T* operator -> () const
130 { return weak_ptr<T>::operator -> (); }
131
136 void reset( T* r = 0 );
137
138 private:
139 friend class WeakObject;
140 friend class rc_ptr_trick;
141 void update();
142 };
143
144
151 template <typename T>
152 class shared_ptr : public weak_shared_ptr<T>
153 {
154 public:
161
162 explicit shared_ptr( ReferenceType t = Weak, T* x = 0,
163 bool externalowner = false );
164 shared_ptr( const shared_ptr<T> & x );
165 shared_ptr( const weak_shared_ptr<T> & x );
166 shared_ptr( const rc_ptr<T> & x );
167 shared_ptr( const weak_ptr<T> & x );
168 ~shared_ptr();
169
170 bool operator == ( const shared_ptr<T> & x ) const
171 { return weak_ptr<T>::operator == (x); }
172 bool operator == ( const T* x ) const
173 { return this->weak_ptr<T>::get() == x; }
174 bool operator == ( const rc_ptr<T> & x ) const
175 { return this->weak_ptr<T>::get() == x.get(); }
176 bool operator == ( const weak_ptr<T> & x ) const
177 { return this->weak_ptr<T>::get() == x.get(); }
178 bool operator == ( const weak_shared_ptr<T> & x ) const
179 { return this->weak_ptr<T>::get() == x.get(); }
180 bool operator != ( const shared_ptr<T> & x ) const
181 { return weak_ptr<T>::operator != (x); }
182 bool operator != ( const T* x ) const
183 { return this->weak_ptr<T>::get() != x; }
184 bool operator != ( const rc_ptr<T> & x ) const
185 { return this->weak_ptr<T>::get() != x.get(); }
186 bool operator != ( const weak_ptr<T> & x ) const
187 { return this->weak_ptr<T>::get() != x.get(); }
188 bool operator != ( const weak_shared_ptr<T> & x ) const
189 { return this->weak_ptr<T>::get() != x.get(); }
190 bool operator < ( const shared_ptr<T> & x ) const
191 { return weak_ptr<T>::operator < (x); }
192 bool operator < ( const rc_ptr<T> & x ) const
193 { return this->weak_ptr<T>::get() < x.get(); }
194 bool operator < ( const weak_ptr<T> & x ) const
195 { return this->weak_ptr<T>::get() < x.get(); }
196 bool operator < ( const weak_shared_ptr<T> & x ) const
197 { return this->weak_ptr<T>::get() < x.get(); }
198
201 shared_ptr<T> & operator = ( const rc_ptr<T> & x );
203 T* release();
204 void reset( ReferenceType t, T* r = 0 );
205
207
208 private:
209 ReferenceType _reftype;
210 };
211
212
213 // ----------------------------
214
215 template <typename T>
216 inline
217 weak_shared_ptr<T>::weak_shared_ptr( T* x, bool externalowner )
218 : rc_ptr<T>( x, externalowner ), weak_ptr<T>( x )
219 {
220 // force re-attaching with the correct type for this
221 if( x )
222 {
223 ++x->weak_count;
224 x->attachWeakPtr( *this );
225 }
226 }
227
228
229 template <typename T>
230 inline
232 : rc_ptr<T>( x ), weak_ptr<T>( x )
233 {
234 // force re-attaching with the correct type for this
235 if( x.get() )
236 {
237 ++x->weak_count;
238 x->attachWeakPtr( *this );
239 }
240 }
241
242
243 template <typename T>
244 inline
246 : rc_ptr<T>( x ), weak_ptr<T>( x.get() )
247 {
248 // force re-attaching with the correct type for this
249 if( x.get() )
250 {
251 ++x->weak_count;
252 x->attachWeakPtr( *this );
253 }
254 }
255
256
257 template <typename T>
258 inline
260 : rc_ptr<T>( x ), weak_ptr<T>( x )
261 {
262 // force re-attaching with the correct type for this
263 if( x.get() )
264 {
265 ++x->weak_count;
266 x->attachWeakPtr( *this );
267 }
268 }
269
270
271 template <typename T>
272 inline
274 {
275 if( get() )
276 --get()->weak_count;
277 }
278
279
280 template <typename T>
281 inline
282 void weak_shared_ptr<T>::update()
283 {
284 // weak_ptr<T>::update(); is done by WeakObject
285 rc_ptr<T>::reset( 0 );
286 }
287
288
289 template <typename T>
290 inline
292 ( const weak_shared_ptr<T> & x )
293 {
294 if( &x == this )
295 return *this;
296
297 if( get() )
298 --get()->weak_count;
300 // force re-attaching with the correct type for this
301 if( x.get() )
302 {
303 ++x->weak_count;
304 x->attachWeakPtr( *this );
305 }
307 return *this;
308 }
309
310
311 template <typename T>
312 inline
314 ( const rc_ptr<T> & x )
315 {
316 if( this != &x )
317 reset( x.get() );
318 return *this;
319 }
320
321
322 template <typename T>
323 inline
325 {
326 if( get() )
327 --get()->weak_count;
329 return rc_ptr<T>::release();
330 }
331
332
333 template <typename T>
334 inline
336 {
337 if( get() )
338 --get()->weak_count;
340 // force re-attaching with the correct type for this
341 if( r )
342 {
343 ++r->weak_count;
344 r->attachWeakPtr( *this );
345 }
346 rc_ptr<T>::reset( r );
347 }
348
349 // ----------------
350
351
352 template <typename T>
353 inline
354 shared_ptr<T>::shared_ptr( ReferenceType t, T* x, bool externalowner )
355 : weak_shared_ptr<T>( x, externalowner ), _reftype( t )
356 {
357 switch( t )
358 {
359 case Strong:
360 if( x )
361 --x->weak_count;
362 break;
363 case WeakShared:
364 break;
365 case Weak:
368 break;
369 }
370 }
371
372
373 template <typename T>
374 inline
376 : weak_shared_ptr<T>( x ), _reftype( x.referenceType() )
377 {
378 switch( referenceType() )
379 {
380 case Strong:
381 if( x.get() )
382 --x->weak_count;
383 break;
384 case WeakShared:
385 break;
386 case Weak:
388 weak_ptr<T>::reset( x.get() );
389 break;
390 }
391 }
392
393
394 template <typename T>
395 inline
397 : weak_shared_ptr<T>( x ), _reftype( WeakShared )
398 {
399 }
400
401
402 template <typename T>
403 inline
405 : weak_shared_ptr<T>( x.get() ), _reftype( Strong )
406 {
407 if( x )
408 --x->weak_count;
409 }
410
411
412 template <typename T>
413 inline
420
421
422 template <typename T>
423 inline
425 {
426 switch( referenceType() )
427 {
428 case Strong:
429 if( this->get() )
430 ++this->get()->weak_count; // as it will be decremented soon
431 // WARNING: this is not thread-safe
432 break;
433 case WeakShared:
434 break;
435 case Weak:
436 release();
437 break;
438 }
439 }
440
441
442 template <typename T>
443 inline typename shared_ptr<T>::ReferenceType
445 {
446 return _reftype;
447 }
448
449
450 template <typename T>
451 inline
453 ( const shared_ptr<T> & x )
454 {
455 reset( x.referenceType(), x.get() );
456 return *this;
457 }
458
459
460 template <typename T>
461 inline
463 ( const weak_shared_ptr<T> & x )
464 {
465 reset( WeakShared, x.get() );
466 return *this;
467 }
468
469
470 template <typename T>
471 inline
473 {
474 reset( Strong, x.get() );
475 return *this;
476 }
477
478
479 template <typename T>
480 inline
482 {
483 reset( Weak, x.get() );
484 return *this;
485 }
486
487
488 template <typename T>
489 inline
491 {
492 T* x = weak_ptr<T>::release();
493 if( this->get() && referenceType() == WeakShared )
494 --this->get()->weak_count;
495 if( referenceType() != Weak )
496 return rc_ptr<T>::release();
497 return x;
498 }
499
500
501 template <typename T>
502 inline
504 {
505 if( r == this->get() )
506 {
507 if( t != referenceType() )
508 {
509 switch( t )
510 {
511 case Strong:
512 switch( referenceType() )
513 {
514 case WeakShared:
515 --r->weak_count;
516 break;
517 case Weak:
518 rc_ptr<T>::reset( r );
519 break;
520 default:
521 break;
522 }
523 break;
524 case WeakShared:
525 switch( referenceType() )
526 {
527 case Strong:
528 ++r->weak_count;
529 break;
530 case Weak:
532 break;
533 default:
534 break;
535 }
536 break;
537 case Weak:
538 switch( referenceType() )
539 {
540 case Strong:
541 rc_ptr<T>::reset( 0 );
542 if( this->get() ) // r could have been destroyed by now
543 r->attachWeakPtr( static_cast<weak_ptr<T> &>( *this ) );
544 break;
545 case WeakShared:
546 if( r->_refCounter == 1 )
547 weak_shared_ptr<T>::reset( 0 ); // should destroy r...
548 else
549 {
552 }
553 break;
554 default:
555 break;
556 }
557 }
558 _reftype = t;
559 }
560 return;
561 }
562
563 if( this->get() )
564 switch( referenceType() )
565 {
566 case Strong:
567 rc_ptr<T>::reset( 0 );
568 break;
569 case WeakShared:
571 break;
572 case Weak:
574 }
575
576 _reftype = t;
577 switch( t )
578 {
579 case Strong:
580 // force re-attaching with the correct type for this
581 if( r )
582 {
583 r->attachWeakPtr( *this );
584 rc_ptr<T>::reset( r );
586 }
587 break;
588 case WeakShared:
589 // force re-attaching with the correct type for this
590 if( r )
592 break;
593 case Weak:
595 break;
596 }
597 }
598
599}
600
601#endif
602
int RefCounterType
Definition rcptr.h:127
bool tryDelete()
tests if the shared object can be deleted.
bool testDeletable()
tests if the shared object can be deleted (no strong pointers to it).
void disableRefCount()
called by destructors to avoid double deletion.
friend class weak_shared_ptr
Definition sharedptr.h:78
friend class shared_ptr
Definition sharedptr.h:79
SharedObject & operator=(const SharedObject &)
Definition sharedptr.h:55
SharedObject(const SharedObject &x)
friend class rc_ptr_trick
Definition sharedptr.h:80
virtual ~SharedObject()
notifies observers
const_ref< T > & operator=(const ref< T > &other)
Definition rcptr.h:427
Reference-counting pointer.
Definition rcptr.h:640
void reset(T *p=NULL)
Definition rcptr.h:664
T * get() const
Definition rcptr.h:666
T * release()
Definition rcptr.h:499
A multi-purpose general smart pointer, which can act as either a rc_ptr, a weak_ptr or a weak_shared_...
Definition sharedptr.h:153
bool operator==(const shared_ptr< T > &x) const
Definition sharedptr.h:170
bool operator<(const shared_ptr< T > &x) const
Definition sharedptr.h:190
shared_ptr< T > & operator=(const shared_ptr< T > &x)
Definition sharedptr.h:453
void reset(ReferenceType t, T *r=0)
Definition sharedptr.h:503
shared_ptr(ReferenceType t=Weak, T *x=0, bool externalowner=false)
Definition sharedptr.h:354
ReferenceType referenceType() const
Definition sharedptr.h:444
bool operator!=(const shared_ptr< T > &x) const
Definition sharedptr.h:180
Observer pointer, observing a shfj::WeakObject.
Definition weakptr.h:69
T * get() const
Definition weakptr.h:227
friend class weak_ptr
Definition weakptr.h:75
bool operator!=(const weak_ptr< T > &x) const
Definition weakptr.h:249
weak_ptr & operator=(const weak_ptr< Y > &r)
Definition weakptr.h:144
T & operator*() const
Definition weakptr.h:217
void reset(T *r=0)
Definition weakptr.h:103
bool operator<(const weak_ptr< T > &x) const
Definition weakptr.h:257
bool operator==(const weak_ptr< T > &x) const
Definition weakptr.h:241
T * operator->() const
Definition weakptr.h:222
weak_shared_ptr: increments a reference count, is told and becomes null whenever the shared object is...
Definition sharedptr.h:95
bool operator==(const T *x) const
Definition sharedptr.h:105
weak_shared_ptr(const weak_shared_ptr< T > &x)
Definition sharedptr.h:231
bool operator<(const weak_shared_ptr< T > &x) const
Definition sharedptr.h:121
T & operator*() const
Definition sharedptr.h:127
bool operator!=(const T *x) const
Definition sharedptr.h:113
weak_shared_ptr< T > & operator=(const weak_shared_ptr< T > &x)
Definition sharedptr.h:292
T * operator->() const
Definition sharedptr.h:129
weak_shared_ptr(const weak_ptr< T > &x)
Definition sharedptr.h:259
weak_shared_ptr(T *x=0, bool externalowner=false)
Definition sharedptr.h:217
weak_shared_ptr(const rc_ptr< T > &x)
Definition sharedptr.h:245