type_traits (add_reference): Robustify vs reference to void.
[platform/upstream/gcc.git] / libstdc++-v3 / include / tr1 / boost_shared_ptr.h
1 // <tr1/boost_shared_ptr.h> -*- C++ -*-
2
3 // Copyright (C) 2005, 2006 Free Software Foundation, Inc.
4 //
5 // This file is part of the GNU ISO C++ Library.  This library is free
6 // software; you can redistribute it and/or modify it under the
7 // terms of the GNU General Public License as published by the
8 // Free Software Foundation; either version 2, or (at your option)
9 // any later version.
10
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 // GNU General Public License for more details.
15
16 // You should have received a copy of the GNU General Public License along
17 // with this library; see the file COPYING.  If not, write to the Free
18 // Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
19 // USA.
20
21 // As a special exception, you may use this file as part of a free software
22 // library without restriction.  Specifically, if other files instantiate
23 // templates or use macros or inline functions from this file, or you compile
24 // this file and link it with other files to produce an executable, this
25 // file does not by itself cause the resulting executable to be covered by
26 // the GNU General Public License.  This exception does not however
27 // invalidate any other reasons why the executable file might be covered by
28 // the GNU General Public License.
29
30 //  shared_count.hpp
31 //  Copyright (c) 2001, 2002, 2003 Peter Dimov and Multi Media Ltd.
32
33 //  shared_ptr.hpp
34 //  Copyright (C) 1998, 1999 Greg Colvin and Beman Dawes.
35 //  Copyright (C) 2001, 2002, 2003 Peter Dimov
36
37 //  weak_ptr.hpp
38 //  Copyright (C) 2001, 2002, 2003 Peter Dimov
39
40 //  enable_shared_from_this.hpp
41 //  Copyright (C) 2002 Peter Dimov
42
43 // Distributed under the Boost Software License, Version 1.0. (See
44 // accompanying file LICENSE_1_0.txt or copy at
45 // http://www.boost.org/LICENSE_1_0.txt)
46
47 // GCC Note:  based on version 1.32.0 of the Boost library.
48
49 /** @file boost_memory.h
50  *  This is an internal header file, included by other library headers.
51  *  You should not attempt to use it directly.
52  */
53
54 #ifndef _BOOST_SHARED_PTR_H
55 #define _BOOST_SHARED_PTR_H 1
56
57 namespace std
58 {
59 _GLIBCXX_BEGIN_NAMESPACE(tr1)
60
61   class bad_weak_ptr : public std::exception
62   {
63   public:
64     virtual char const*
65     what() const throw()
66     { return "tr1::bad_weak_ptr"; }
67   };
68
69   // Substitute for bad_weak_ptr object in the case of -fno-exceptions.
70   inline void
71   __throw_bad_weak_ptr()
72   {
73 #if __EXCEPTIONS
74     throw bad_weak_ptr();
75 #else
76     std::abort();
77 #endif
78   }
79
80   using __gnu_cxx::_Lock_policy;
81   using __gnu_cxx::__default_lock_policy;
82   using __gnu_cxx::_S_single;
83   using __gnu_cxx::_S_mutex;
84   using __gnu_cxx::_S_atomic;
85
86   template<typename _Tp>
87     struct _Sp_deleter
88     {
89       typedef void result_type;
90       typedef _Tp* argument_type;
91
92       void
93       operator()(_Tp* __p) const
94       { delete __p; }
95     };
96
97   // Empty helper class except when the template argument is _S_mutex.
98   template<_Lock_policy _Lp>
99     class _Mutex_base
100     { };
101
102   template<>
103     class _Mutex_base<_S_mutex> : public __gnu_cxx::__mutex
104     { };
105
106   template<_Lock_policy _Lp = __default_lock_policy>
107     class _Sp_counted_base : public _Mutex_base<_Lp>
108     {
109     public:  
110       _Sp_counted_base() : _M_use_count(1), _M_weak_count(1) { }
111       
112       virtual
113       ~_Sp_counted_base() // nothrow 
114       { }
115   
116       // Called when _M_use_count drops to zero, to release the resources
117       // managed by *this.
118       virtual void
119       dispose() = 0; // nothrow
120       
121       // Called when _M_weak_count drops to zero.
122       virtual void
123       destroy() // nothrow
124       { delete this; }
125       
126       virtual void*
127       get_deleter(const std::type_info&) = 0;
128       
129       void
130       add_ref_copy()
131       { __gnu_cxx::__atomic_add(&_M_use_count, 1); }
132   
133       void
134       add_ref_lock();
135       
136       void
137       release() // nothrow
138       {
139         if (__gnu_cxx::__exchange_and_add(&_M_use_count, -1) == 1)
140           {
141             dispose();
142 #ifdef __GTHREADS       
143             _GLIBCXX_READ_MEM_BARRIER;
144             _GLIBCXX_WRITE_MEM_BARRIER;
145 #endif
146             if (__gnu_cxx::__exchange_and_add(&_M_weak_count, -1) == 1)
147               destroy();
148           }
149       }
150   
151       void
152       weak_add_ref() // nothrow
153       { __gnu_cxx::__atomic_add(&_M_weak_count, 1); }
154   
155       void
156       weak_release() // nothrow
157       {
158         if (__gnu_cxx::__exchange_and_add(&_M_weak_count, -1) == 1)
159           {
160 #ifdef __GTHREADS
161             _GLIBCXX_READ_MEM_BARRIER;
162             _GLIBCXX_WRITE_MEM_BARRIER;
163 #endif
164             destroy();
165           }
166       }
167   
168       long
169       use_count() const // nothrow
170       { return _M_use_count; }  // XXX is this MT safe? 
171       
172     private:  
173       _Sp_counted_base(_Sp_counted_base const&);
174       _Sp_counted_base& operator=(_Sp_counted_base const&);
175       
176       _Atomic_word _M_use_count;        // #shared
177       _Atomic_word _M_weak_count;       // #weak + (#shared != 0)
178     };
179
180   template<>
181     inline void
182     _Sp_counted_base<_S_single>::add_ref_lock()
183     {
184       if (__gnu_cxx::__exchange_and_add(&_M_use_count, 1) == 0)
185         {
186           _M_use_count = 0;
187           __throw_bad_weak_ptr();
188         }
189     }
190   
191 #ifdef __GTHREADS
192   template<>
193     inline void
194     _Sp_counted_base<_S_mutex>::add_ref_lock()
195     {
196       __gnu_cxx::__scoped_lock sentry(*this);
197       if (__gnu_cxx::__exchange_and_add(&_M_use_count, 1) == 0)
198         {
199           _M_use_count = 0;
200           __throw_bad_weak_ptr();
201         }
202     }
203 #endif
204
205   template<> 
206     inline void
207     _Sp_counted_base<_S_atomic>::add_ref_lock()
208     {
209       // Perform lock-free add-if-not-zero operation.
210       _Atomic_word __count;
211       do
212         {
213           __count = _M_use_count;
214           if (__count == 0)
215             __throw_bad_weak_ptr();
216           
217           // Replace the current counter value with the old value + 1, as
218           // long as it's not changed meanwhile. 
219         }
220       while (!__sync_bool_compare_and_swap(&_M_use_count, __count,
221                                            __count + 1));
222     }
223
224   template<typename _Ptr, typename _Deleter, _Lock_policy _Lp>
225     class _Sp_counted_base_impl : public _Sp_counted_base<_Lp>
226     {
227     public:
228       /**
229        *  @brief   
230        *  @pre     d(p) must not throw.
231        */
232       _Sp_counted_base_impl(_Ptr __p, _Deleter __d)
233       : _M_ptr(__p), _M_del(__d) { }
234     
235       virtual void
236       dispose() // nothrow
237       { _M_del(_M_ptr); }
238       
239       virtual void*
240       get_deleter(const std::type_info& __ti)
241       { return __ti == typeid(_Deleter) ? &_M_del : 0; }
242       
243     private:
244       _Sp_counted_base_impl(const _Sp_counted_base_impl&);
245       _Sp_counted_base_impl& operator=(const _Sp_counted_base_impl&);
246       
247       _Ptr     _M_ptr; // copy constructor must not throw
248       _Deleter _M_del; // copy constructor must not throw
249     };
250
251   template<_Lock_policy _Lp = __default_lock_policy>
252     class weak_count;
253
254   template<_Lock_policy _Lp = __default_lock_policy>
255     class shared_count
256     {
257     private:  
258       _Sp_counted_base<_Lp>* _M_pi;
259   
260       friend class weak_count<_Lp>;
261   
262     public: 
263       shared_count() : _M_pi(0) // nothrow
264       { }
265   
266       template<typename _Ptr, typename _Deleter>
267         shared_count(_Ptr __p, _Deleter __d) : _M_pi(0)
268         {
269           try
270             {
271               _M_pi = new _Sp_counted_base_impl<_Ptr, _Deleter, _Lp>(__p, __d);
272             }
273           catch(...)
274             {
275               __d(__p); // Call _Deleter on __p.
276               __throw_exception_again;
277             }
278         }
279       
280       // Special case for auto_ptr<_Tp> to provide the strong guarantee.
281       template<typename _Tp>
282         explicit
283         shared_count(std::auto_ptr<_Tp>& __r)
284         : _M_pi(new _Sp_counted_base_impl<_Tp*,
285                 _Sp_deleter<_Tp>, _Lp >(__r.get(), _Sp_deleter<_Tp>()))
286         { __r.release(); }
287   
288       // Throw bad_weak_ptr when __r.use_count() == 0.
289       explicit shared_count(const weak_count<_Lp>& __r);
290   
291       ~shared_count() // nothrow
292       {
293         if (_M_pi != 0)
294           _M_pi->release();
295       }
296       
297       shared_count(const shared_count& __r)
298       : _M_pi(__r._M_pi) // nothrow
299       {
300         if (_M_pi != 0)
301           _M_pi->add_ref_copy();
302       }
303   
304       shared_count&
305       operator=(const shared_count& __r) // nothrow
306       {
307         _Sp_counted_base<_Lp>* __tmp = __r._M_pi;
308         if (__tmp != _M_pi)
309           {
310             if (__tmp != 0)
311               __tmp->add_ref_copy();
312             if (_M_pi != 0)
313               _M_pi->release();
314             _M_pi = __tmp;
315           }
316         return *this;
317       }
318   
319       void
320       swap(shared_count& __r) // nothrow
321       {
322         _Sp_counted_base<_Lp>* __tmp = __r._M_pi;
323         __r._M_pi = _M_pi;
324         _M_pi = __tmp;
325       }
326   
327       long
328       use_count() const // nothrow
329       { return _M_pi != 0 ? _M_pi->use_count() : 0; }
330       
331       bool
332       unique() const // nothrow
333       { return this->use_count() == 1; }
334       
335       friend inline bool
336       operator==(const shared_count& __a, const shared_count& __b)
337       { return __a._M_pi == __b._M_pi; }
338   
339       friend inline bool
340       operator<(const shared_count& __a, const shared_count& __b)
341       { return std::less<_Sp_counted_base<_Lp>*>()(__a._M_pi, __b._M_pi); }
342   
343       void*
344       get_deleter(const std::type_info& __ti) const
345       { return _M_pi ? _M_pi->get_deleter(__ti) : 0; }
346     };
347
348   template<_Lock_policy _Lp>
349     class weak_count
350     {
351     private:  
352       _Sp_counted_base<_Lp>* _M_pi;
353       
354       friend class shared_count<_Lp>;
355       
356     public:  
357       weak_count()
358       : _M_pi(0) // nothrow
359       { }
360   
361       weak_count(const shared_count<_Lp>& __r)
362       : _M_pi(__r._M_pi) // nothrow
363       {
364         if (_M_pi != 0)
365           _M_pi->weak_add_ref();
366       }
367       
368       weak_count(const weak_count<_Lp>& __r)
369       : _M_pi(__r._M_pi) // nothrow
370       {
371         if (_M_pi != 0)
372           _M_pi->weak_add_ref();
373       }
374       
375       ~weak_count() // nothrow
376       {
377         if (_M_pi != 0)
378           _M_pi->weak_release();
379       }
380       
381       weak_count<_Lp>&
382       operator=(const shared_count<_Lp>& __r) // nothrow
383       {
384         _Sp_counted_base<_Lp>* __tmp = __r._M_pi;
385         if (__tmp != 0)
386           __tmp->weak_add_ref();
387         if (_M_pi != 0)
388           _M_pi->weak_release();
389         _M_pi = __tmp;  
390         return *this;
391       }
392       
393       weak_count<_Lp>&
394       operator=(const weak_count<_Lp>& __r) // nothrow
395       {
396         _Sp_counted_base<_Lp> * __tmp = __r._M_pi;
397         if (__tmp != 0)
398           __tmp->weak_add_ref();
399         if (_M_pi != 0)
400           _M_pi->weak_release();
401         _M_pi = __tmp;
402         return *this;
403       }
404   
405       void
406       swap(weak_count<_Lp>& __r) // nothrow
407       {
408         _Sp_counted_base<_Lp> * __tmp = __r._M_pi;
409         __r._M_pi = _M_pi;
410         _M_pi = __tmp;
411       }
412   
413       long
414       use_count() const // nothrow
415       { return _M_pi != 0 ? _M_pi->use_count() : 0; }
416       
417       friend inline bool
418       operator==(const weak_count<_Lp>& __a, const weak_count<_Lp>& __b)
419       { return __a._M_pi == __b._M_pi; }
420       
421       friend inline bool
422       operator<(const weak_count<_Lp>& __a, const weak_count<_Lp>& __b)
423       { return std::less<_Sp_counted_base<_Lp>*>()(__a._M_pi, __b._M_pi); }
424     };
425
426   template<_Lock_policy _Lp>
427     inline
428     shared_count<_Lp>::
429     shared_count(const weak_count<_Lp>& __r)
430     : _M_pi(__r._M_pi)
431     {
432       if (_M_pi != 0)
433         _M_pi->add_ref_lock();
434       else
435         __throw_bad_weak_ptr();
436     }
437   
438
439   // Forward decls.
440   template<typename _Tp, _Lock_policy _Lp = __default_lock_policy>
441     class __shared_ptr;
442   
443   template<typename _Tp, _Lock_policy _Lp = __default_lock_policy>
444     class __weak_ptr;
445
446   template<typename _Tp, _Lock_policy _Lp>
447     class __enable_shared_from_this;
448
449   struct __static_cast_tag { };
450   struct __const_cast_tag { };
451   struct __dynamic_cast_tag { };
452   struct __polymorphic_cast_tag { };
453
454
455   // Support for enable_shared_from_this.
456
457   // Friend of __enable_shared_from_this.
458   template<_Lock_policy _Lp, typename _Tp1, typename _Tp2>
459     void
460     __enable_shared_from_this_helper(const shared_count<_Lp>&,
461                                      const __enable_shared_from_this<_Tp1,
462                                      _Lp>*, const _Tp2*);
463
464   template<_Lock_policy _Lp>
465     inline void
466     __enable_shared_from_this_helper(const shared_count<_Lp>&, ...)
467     { }
468
469
470   /**
471    *  @class shared_ptr <tr1/memory>
472    *
473    *  A smart pointer with reference-counted copy semantics.
474    *  The object pointed to is deleted when the last shared_ptr pointing to
475    *  it is destroyed or reset.
476    */
477   template<typename _Tp, _Lock_policy _Lp>
478     class __shared_ptr
479     {
480     public:
481       typedef _Tp   element_type;
482       
483       /** @brief  Construct an empty %__shared_ptr.
484        *  @post   use_count()==0 && get()==0
485        */
486       __shared_ptr()
487       : _M_ptr(0), _M_refcount() // never throws
488       { }
489
490       /** @brief  Construct a %__shared_ptr that owns the pointer @a p.
491        *  @param  p  A pointer that is convertible to element_type*.
492        *  @post   use_count() == 1 && get() == p
493        *  @throw  std::bad_alloc, in which case @c delete @a p is called.
494        */
495       template<typename _Tp1>
496         explicit
497         __shared_ptr(_Tp1* __p)
498         : _M_ptr(__p), _M_refcount(__p, _Sp_deleter<_Tp1>())
499         {
500           __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>)
501           // __glibcxx_function_requires(_CompleteConcept<_Tp1*>)
502           __enable_shared_from_this_helper( _M_refcount, __p, __p );
503         }
504
505       //
506       // Requirements: D's copy constructor and destructor must not throw
507       //
508       // __shared_ptr will release p by calling d(p)
509       //
510       /** @brief  Construct a %__shared_ptr that owns the pointer @a p
511        *          and the deleter @a d.
512        *  @param  p  A pointer.
513        *  @param  d  A deleter.
514        *  @post   use_count() == 1 && get() == p
515        *  @throw  std::bad_alloc, in which case @a d(p) is called.
516        */
517       template<typename _Tp1, typename _Deleter>
518         __shared_ptr(_Tp1* __p, _Deleter __d)
519         : _M_ptr(__p), _M_refcount(__p, __d)
520         {
521           __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>)
522           // TODO requires D is CopyConstructible and d(p) well-formed
523           __enable_shared_from_this_helper( _M_refcount, __p, __p );
524         }
525       
526       //  generated copy constructor, assignment, destructor are fine.
527       
528       /** @brief  If @a r is empty, constructs an empty %__shared_ptr;
529        *          otherwise construct a %__shared_ptr that shares ownership
530        *          with @a r.
531        *  @param  r  A %__shared_ptr.
532        *  @post   get() == r.get() && use_count() == r.use_count()
533        *  @throw  std::bad_alloc, in which case 
534        */
535       template<typename _Tp1>
536         __shared_ptr(const __shared_ptr<_Tp1, _Lp>& __r)
537         : _M_ptr(__r._M_ptr), _M_refcount(__r._M_refcount) // never throws
538         { __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>) }
539
540       /** @brief  Constructs a %__shared_ptr that shares ownership with @a r
541        *          and stores a copy of the pointer stored in @a r.
542        *  @param  r  A weak_ptr.
543        *  @post   use_count() == r.use_count()
544        *  @throw  bad_weak_ptr when r.expired(),
545        *          in which case the constructor has no effect.
546        */
547       template<typename _Tp1>
548         explicit
549         __shared_ptr(const __weak_ptr<_Tp1, _Lp>& __r)
550         : _M_refcount(__r._M_refcount) // may throw
551         {
552           __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>)
553           // It is now safe to copy r__._M_ptr, as _M_refcount(__r._M_refcount)
554           // did not throw.
555           _M_ptr = __r._M_ptr;
556         }
557
558       /**
559        * @post use_count() == 1 and r.get() == 0
560        */
561       template<typename _Tp1>
562         explicit
563         __shared_ptr(std::auto_ptr<_Tp1>& __r)
564         : _M_ptr(__r.get()), _M_refcount()
565         {
566           // TODO requires r.release() convertible to _Tp*, Tp1 is complete,
567           // delete r.release() well-formed
568           _Tp1 * __tmp = __r.get();
569           _M_refcount = shared_count<_Lp>(__r);
570           __enable_shared_from_this_helper(_M_refcount, __tmp, __tmp );
571         }
572
573       template<typename _Tp1>
574         __shared_ptr(const __shared_ptr<_Tp1, _Lp>& __r, __static_cast_tag)
575         : _M_ptr(static_cast<element_type*>(__r._M_ptr)),
576           _M_refcount(__r._M_refcount)
577         { }
578
579       template<typename _Tp1>
580         __shared_ptr(const __shared_ptr<_Tp1, _Lp>& __r, __const_cast_tag)
581         : _M_ptr(const_cast<element_type*>(__r._M_ptr)),
582           _M_refcount(__r._M_refcount)
583         { }
584
585       template<typename _Tp1>
586         __shared_ptr(const __shared_ptr<_Tp1, _Lp>& __r, __dynamic_cast_tag)
587         : _M_ptr(dynamic_cast<element_type*>(__r._M_ptr)),
588           _M_refcount(__r._M_refcount)
589         {
590           if (_M_ptr == 0) // need to allocate new counter -- the cast failed
591             _M_refcount = shared_count<_Lp>();
592         }
593       
594       template<typename _Tp1>
595         __shared_ptr&
596         operator=(const __shared_ptr<_Tp1, _Lp>& __r) // never throws
597         {
598           _M_ptr = __r._M_ptr;
599           _M_refcount = __r._M_refcount; // shared_count::op= doesn't throw
600           return *this;
601         }
602
603       template<typename _Tp1>
604         __shared_ptr&
605         operator=(std::auto_ptr<_Tp1>& __r)
606         {
607           __shared_ptr(__r).swap(*this);
608           return *this;
609         }
610
611       void
612       reset() // never throws
613       { __shared_ptr().swap(*this); }
614
615       template<typename _Tp1>
616         void
617         reset(_Tp1* __p) // _Tp1 must be complete.
618         {
619           // Catch self-reset errors.
620           _GLIBCXX_DEBUG_ASSERT(__p == 0 || __p != _M_ptr); 
621           __shared_ptr(__p).swap(*this);
622         }
623
624       template<typename _Tp1, typename _Deleter>
625         void
626         reset(_Tp1 * __p, _Deleter __d)
627         { __shared_ptr(__p, __d).swap(*this); }
628
629       // Allow instantiation when _Tp is [cv-qual] void.
630       typename add_reference<_Tp>::type
631       operator*() const // never throws
632       {
633         _GLIBCXX_DEBUG_ASSERT(_M_ptr != 0);
634         return *_M_ptr;
635       }
636
637       _Tp*
638       operator->() const // never throws
639       {
640         _GLIBCXX_DEBUG_ASSERT(_M_ptr != 0);
641         return _M_ptr;
642       }
643     
644       _Tp*
645       get() const // never throws
646       { return _M_ptr; }
647
648       // Implicit conversion to "bool"
649     private:
650       typedef _Tp* __shared_ptr::*__unspecified_bool_type;
651
652     public:
653       operator __unspecified_bool_type() const // never throws
654       { return _M_ptr == 0 ? 0 : &__shared_ptr::_M_ptr; }
655
656       bool
657       unique() const // never throws
658       { return _M_refcount.unique(); }
659
660       long
661       use_count() const // never throws
662       { return _M_refcount.use_count(); }
663
664       void
665       swap(__shared_ptr<_Tp, _Lp>& __other) // never throws
666       {
667         std::swap(_M_ptr, __other._M_ptr);
668         _M_refcount.swap(__other._M_refcount);
669       }
670
671     private:
672       void*
673       _M_get_deleter(const std::type_info& __ti) const
674       { return _M_refcount.get_deleter(__ti); }
675
676       template<typename _Tp1, _Lock_policy _Lp1>
677         bool
678         _M_less(const __shared_ptr<_Tp1, _Lp1>& __rhs) const
679         { return _M_refcount < __rhs._M_refcount; }
680
681       template<typename _Tp1, _Lock_policy _Lp1> friend class __shared_ptr;
682       template<typename _Tp1, _Lock_policy _Lp1> friend class __weak_ptr;
683
684       template<typename _Del, typename _Tp1, _Lock_policy _Lp1>
685         friend _Del* get_deleter(const __shared_ptr<_Tp1, _Lp1>&);
686
687       // Friends injected into enclosing namespace and found by ADL:
688       template<typename _Tp1>
689         friend inline bool
690         operator==(const __shared_ptr& __a, const __shared_ptr<_Tp1, _Lp>& __b)
691         { return __a.get() == __b.get(); }
692
693       template<typename _Tp1>
694         friend inline bool
695         operator!=(const __shared_ptr& __a, const __shared_ptr<_Tp1, _Lp>& __b)
696         { return __a.get() != __b.get(); }
697
698       template<typename _Tp1>
699         friend inline bool
700         operator<(const __shared_ptr& __a, const __shared_ptr<_Tp1, _Lp>& __b)
701         { return __a._M_less(__b); }
702
703       _Tp*                      _M_ptr;         // Contained pointer.
704       shared_count<_Lp>         _M_refcount;    // Reference counter.
705     };
706
707   // 2.2.3.8 shared_ptr specialized algorithms.
708   template<typename _Tp, _Lock_policy _Lp>
709     inline void
710     swap(__shared_ptr<_Tp, _Lp>& __a, __shared_ptr<_Tp, _Lp>& __b)
711     { __a.swap(__b); }
712
713   // 2.2.3.9 shared_ptr casts
714   /** @warning The seemingly equivalent
715    *           <code>shared_ptr<T>(static_cast<T*>(r.get()))</code>
716    *           will eventually result in undefined behaviour,
717    *           attempting to delete the same object twice.
718    */
719   template<typename _Tp, typename _Tp1, _Lock_policy _Lp>
720     __shared_ptr<_Tp, _Lp>
721     static_pointer_cast(const __shared_ptr<_Tp1, _Lp>& __r)
722     { return __shared_ptr<_Tp, _Lp>(__r, __static_cast_tag()); }
723
724   /** @warning The seemingly equivalent
725    *           <code>shared_ptr<T>(const_cast<T*>(r.get()))</code>
726    *           will eventually result in undefined behaviour,
727    *           attempting to delete the same object twice.
728    */
729   template<typename _Tp, typename _Tp1, _Lock_policy _Lp>
730     __shared_ptr<_Tp, _Lp>
731     const_pointer_cast(const __shared_ptr<_Tp1, _Lp>& __r)
732     { return __shared_ptr<_Tp, _Lp>(__r, __const_cast_tag()); }
733
734   /** @warning The seemingly equivalent
735    *           <code>shared_ptr<T>(dynamic_cast<T*>(r.get()))</code>
736    *           will eventually result in undefined behaviour,
737    *           attempting to delete the same object twice.
738    */
739   template<typename _Tp, typename _Tp1, _Lock_policy _Lp>
740     __shared_ptr<_Tp, _Lp>
741     dynamic_pointer_cast(const __shared_ptr<_Tp1, _Lp>& __r)
742     { return __shared_ptr<_Tp, _Lp>(__r, __dynamic_cast_tag()); }
743
744   // 2.2.3.7 shared_ptr I/O
745   template<typename _Ch, typename _Tr, typename _Tp, _Lock_policy _Lp>
746     std::basic_ostream<_Ch, _Tr>&
747     operator<<(std::basic_ostream<_Ch, _Tr>& __os, 
748                const __shared_ptr<_Tp, _Lp>& __p)
749     {
750       __os << __p.get();
751       return __os;
752     }
753
754   // 2.2.3.10 shared_ptr get_deleter (experimental)
755   template<typename _Del, typename _Tp, _Lock_policy _Lp>
756     inline _Del*
757     get_deleter(const __shared_ptr<_Tp, _Lp>& __p)
758     { return static_cast<_Del*>(__p._M_get_deleter(typeid(_Del))); }
759
760
761   template<typename _Tp, _Lock_policy _Lp>
762     class __weak_ptr
763     {
764     public:
765       typedef _Tp element_type;
766       
767       __weak_ptr() : _M_ptr(0), _M_refcount() // never throws
768       { }
769
770       // Generated copy constructor, assignment, destructor are fine.
771       
772       // The "obvious" converting constructor implementation:
773       //
774       //  template<class Y>
775       //    __weak_ptr(__weak_ptr<Y> const & r)
776       //    : _M_ptr(r._M_ptr), _M_refcount(r._M_refcount) // never throws
777       //    { }
778       //
779       // has a serious problem.
780       //
781       //  r._M_ptr may already have been invalidated. The _M_ptr(r._M_ptr)
782       //  conversion may require access to *r._M_ptr (virtual inheritance).
783       //
784       // It is not possible to avoid spurious access violations since
785       // in multithreaded programs r._M_ptr may be invalidated at any point.
786       template<typename _Tp1>
787         __weak_ptr(const __weak_ptr<_Tp1, _Lp>& __r)
788         : _M_refcount(__r._M_refcount) // never throws
789         {
790           __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>)
791             _M_ptr = __r.lock().get();
792         }
793
794       template<typename _Tp1>
795         __weak_ptr(const __shared_ptr<_Tp1, _Lp>& __r)
796         : _M_ptr(__r._M_ptr), _M_refcount(__r._M_refcount) // never throws
797         { __glibcxx_function_requires(_ConvertibleConcept<_Tp1*, _Tp*>) }
798
799       template<typename _Tp1>
800         __weak_ptr&
801         operator=(const __weak_ptr<_Tp1, _Lp>& __r) // never throws
802         {
803           _M_ptr = __r.lock().get();
804           _M_refcount = __r._M_refcount;
805           return *this;
806         }
807       
808       template<typename _Tp1>
809         __weak_ptr&
810         operator=(const __shared_ptr<_Tp1, _Lp>& __r) // never throws
811         {
812           _M_ptr = __r._M_ptr;
813           _M_refcount = __r._M_refcount;
814           return *this;
815         }
816
817       __shared_ptr<_Tp, _Lp>
818       lock() const // never throws
819       {
820 #ifdef __GTHREADS
821         // Optimization: avoid throw overhead.
822         if (expired())
823           return __shared_ptr<element_type, _Lp>();
824       
825         try
826           {
827             return __shared_ptr<element_type, _Lp>(*this);
828           }
829         catch (const bad_weak_ptr&)
830           {
831             // Q: How can we get here?
832             // A: Another thread may have invalidated r after the
833             //    use_count test above.
834             return __shared_ptr<element_type>();
835           }
836         
837 #else
838         // Optimization: avoid try/catch overhead when single threaded.
839         return expired() ? __shared_ptr<element_type, _Lp>()
840                          : __shared_ptr<element_type, _Lp>(*this);
841
842 #endif
843       } // XXX MT
844
845       long
846       use_count() const // never throws
847       { return _M_refcount.use_count(); }
848
849       bool
850       expired() const // never throws
851       { return _M_refcount.use_count() == 0; }
852       
853       void
854       reset() // never throws
855       { __weak_ptr().swap(*this); }
856
857       void
858       swap(__weak_ptr& __s) // never throws
859       {
860         std::swap(_M_ptr, __s._M_ptr);
861         _M_refcount.swap(__s._M_refcount);
862       }
863
864     private:
865       template<typename _Tp1>
866         bool
867         _M_less(const __weak_ptr<_Tp1, _Lp>& __rhs) const
868         { return _M_refcount < __rhs._M_refcount; }
869
870       // Used by __enable_shared_from_this.
871       void
872       _M_assign(_Tp* __ptr, const shared_count<_Lp>& __refcount)
873       {
874         _M_ptr = __ptr;
875         _M_refcount = __refcount;
876       }
877
878       // Friend injected into namespace and found by ADL.
879       template<typename _Tp1>
880         friend inline bool
881         operator<(const __weak_ptr& __lhs, const __weak_ptr<_Tp1, _Lp>& __rhs)
882         { return __lhs._M_less(__rhs); }
883       
884       template<typename _Tp1, _Lock_policy _Lp1> friend class __weak_ptr;
885       template<typename _Tp1, _Lock_policy _Lp1> friend class __shared_ptr;
886       friend class __enable_shared_from_this<_Tp, _Lp>;
887       
888       _Tp*                      _M_ptr;           // Contained pointer.
889       weak_count<_Lp>           _M_refcount;      // Reference counter.
890     };
891
892   // 2.2.4.7 weak_ptr specialized algorithms.
893   template<typename _Tp, _Lock_policy _Lp>
894     void
895     swap(__weak_ptr<_Tp, _Lp>& __a, __weak_ptr<_Tp, _Lp>& __b)
896     { __a.swap(__b); }
897
898
899   template<typename _Tp, _Lock_policy _Lp = __default_lock_policy>
900     class __enable_shared_from_this
901     {
902     protected:
903       __enable_shared_from_this() { }
904       
905       __enable_shared_from_this(const __enable_shared_from_this&) { }
906       
907       __enable_shared_from_this&
908       operator=(const __enable_shared_from_this&)
909       { return *this; }
910
911       ~__enable_shared_from_this() { }
912       
913     public:
914       __shared_ptr<_Tp, _Lp>
915       shared_from_this()
916       {
917         __shared_ptr<_Tp, _Lp> __p(this->_M_weak_this);
918         return __p;
919       }
920       
921       __shared_ptr<const _Tp, _Lp>
922       shared_from_this() const
923       {
924         __shared_ptr<const _Tp, _Lp> __p(this->_M_weak_this);
925         return __p;
926       }
927       
928     private:
929       template<typename _Tp1>
930         void
931         _M_weak_assign(_Tp1* __p, const shared_count<_Lp>& __n) const
932         { _M_weak_this._M_assign(__p, __n); }
933
934       template<typename _Tp1>
935         friend void
936         __enable_shared_from_this_helper(const shared_count<_Lp>& __pn,
937                                          const __enable_shared_from_this* __pe,
938                                          const _Tp1* __px)
939         {
940           if (__pe != 0)
941             __pe->_M_weak_assign(const_cast<_Tp1*>(__px), __pn);
942         }
943       
944       mutable __weak_ptr<_Tp, _Lp> _M_weak_this;
945     };
946
947   template<typename _Tp>
948     class shared_ptr;
949
950   // The actual TR1 weak_ptr, with forwarding constructors and
951   // assignment operators.
952   template<typename _Tp>
953     class weak_ptr : public __weak_ptr<_Tp>
954     {
955     public:
956       weak_ptr()
957       : __weak_ptr<_Tp>() { }
958       
959       template<typename _Tp1>
960         weak_ptr(const __weak_ptr<_Tp1>& __r)
961         : __weak_ptr<_Tp>(__r) { }
962     
963       template<typename _Tp1>
964         weak_ptr(const __shared_ptr<_Tp1>& __r)
965         : __weak_ptr<_Tp>(__r) { }
966
967       template<typename _Tp1>
968         weak_ptr&
969         operator=(const weak_ptr<_Tp1>& __r) // never throws
970         {
971           this->__weak_ptr<_Tp>::operator=(__r);
972           return *this;
973         }
974
975       template<typename _Tp1>
976         weak_ptr&
977         operator=(const shared_ptr<_Tp1>& __r) // never throws
978         {
979           this->__weak_ptr<_Tp>::operator=(__r);
980           return *this;
981         }
982     };
983
984   // The actual TR1 shared_ptr, with forwarding constructors and
985   // assignment operators.
986   template<typename _Tp>
987     class shared_ptr : public __shared_ptr<_Tp>
988     {
989     public:
990       shared_ptr() : __shared_ptr<_Tp>() { }
991       
992       template<typename _Tp1>
993         explicit
994         shared_ptr(_Tp1* __p)
995         : __shared_ptr<_Tp>(__p) { }
996     
997       template<typename _Tp1, typename _Deleter>
998         shared_ptr(_Tp1* __p, _Deleter __d)
999         : __shared_ptr<_Tp>(__p, __d) { }
1000     
1001       template<typename _Tp1>
1002         shared_ptr(const __shared_ptr<_Tp1>& __r)
1003         : __shared_ptr<_Tp>(__r) { }
1004     
1005       template<typename _Tp1>
1006         explicit
1007         shared_ptr(const __weak_ptr<_Tp1>& __r)
1008         : __shared_ptr<_Tp>(__r) { }
1009     
1010       template<typename _Tp1>
1011         explicit
1012         shared_ptr(std::auto_ptr<_Tp1>& __r)
1013         : __shared_ptr<_Tp>(__r) { }
1014
1015       template<typename _Tp1>
1016         shared_ptr(const __shared_ptr<_Tp1>& __r, __static_cast_tag)
1017         : __shared_ptr<_Tp>(__r, __static_cast_tag()) { }
1018
1019       template<typename _Tp1>
1020         shared_ptr(const __shared_ptr<_Tp1>& __r, __const_cast_tag)
1021         : __shared_ptr<_Tp>(__r, __const_cast_tag()) { }
1022     
1023       template<typename _Tp1>
1024         shared_ptr(const __shared_ptr<_Tp1>& __r, __dynamic_cast_tag)
1025         : __shared_ptr<_Tp>(__r, __dynamic_cast_tag()) { }
1026
1027       // Additional non-base assignment operators to avoid excessive errors.
1028       template<typename _Tp1>
1029         shared_ptr&
1030         operator=(std::auto_ptr<_Tp1>& __r)
1031         {
1032           this->__shared_ptr<_Tp>::operator=(__r);
1033           return *this;
1034         }
1035
1036       template<typename _Tp1>
1037         shared_ptr&
1038         operator=(const shared_ptr<_Tp1>& __r) // never throws
1039         {
1040           this->__shared_ptr<_Tp>::operator=(__r);
1041           return *this;
1042         }
1043     };
1044
1045   template<typename _Tp>
1046     class enable_shared_from_this : public __enable_shared_from_this<_Tp>
1047     {
1048     protected:
1049       enable_shared_from_this()
1050       : __enable_shared_from_this<_Tp>() { }
1051       
1052       enable_shared_from_this(const enable_shared_from_this&)
1053       : __enable_shared_from_this<_Tp>(enable_shared_from_this<_Tp>()) { }
1054     };
1055   
1056 _GLIBCXX_END_NAMESPACE
1057 } // namespace std
1058
1059 #endif