enable_shared_from_this-related fixes.

[SVN r16341]
This commit is contained in:
Peter Dimov
2002-11-20 12:38:51 +00:00
parent 4b200e9847
commit 804b1483c7
4 changed files with 42 additions and 35 deletions

View File

@ -72,7 +72,10 @@ int main()
return boost::report_errors();
}
class impl: public X, public Y, public boost::enable_shared_from_this<impl>
// virtual inheritance from Y to stress the implementation
// (prevents Y* -> impl* casts)
class impl: public X, public virtual Y, public boost::enable_shared_from_this<impl>
{
public:
@ -88,8 +91,14 @@ public:
}
};
// intermediate impl2 to stress the implementation
class impl2: public impl
{
};
boost::shared_ptr<Y> createY()
{
boost::shared_ptr<impl> pi(new impl);
boost::shared_ptr<Y> pi(new impl2);
return pi;
}

View File

@ -28,28 +28,20 @@ public:
shared_ptr<T> shared_from_this()
{
shared_ptr<T> p(weak_this);
shared_ptr<T> p(_internal_weak_this);
BOOST_ASSERT(p.get() == this);
return p;
}
shared_ptr<T const> shared_from_this() const
{
shared_ptr<T const> p(weak_this);
shared_ptr<T const> p(_internal_weak_this);
BOOST_ASSERT(p.get() == this);
return p;
}
#ifndef BOOST_NO_MEMBER_TEMPLATE_FRIENDS
private:
template<class Y> friend class shared_ptr;
#endif
typedef T element_type; // for bcc 5.5.1
weak_ptr<element_type> weak_this;
typedef T _internal_element_type; // for bcc 5.5.1
weak_ptr<_internal_element_type> _internal_weak_this;
};
} // namespace boost

View File

@ -39,6 +39,9 @@
namespace boost
{
template<class T> class weak_ptr;
template<class T> class enable_shared_from_this;
namespace detail
{
@ -65,6 +68,17 @@ template<> struct shared_ptr_traits<void const>
#endif
// enable_shared_from_this support
template<class T, class Y> void sp_enable_shared_from_this(boost::enable_shared_from_this<T> * pe, Y * px, shared_count const & pn)
{
pe->_internal_weak_this._internal_assign(px, pn);
}
void sp_enable_shared_from_this(void const *, void const *, shared_count const &)
{
}
} // namespace detail
@ -76,9 +90,6 @@ template<> struct shared_ptr_traits<void const>
// is destroyed or reset.
//
template<class T> class weak_ptr;
template<class T> class enable_shared_from_this;
template<class T> class shared_ptr
{
private:
@ -86,17 +97,6 @@ private:
// Borland 5.5.1 specific workaround
typedef shared_ptr<T> this_type;
// enable_shared_from_this support
template<class Y> void sp_enable_shared_from_this(boost::enable_shared_from_this<Y> * q)
{
q->weak_this = *this;
}
void sp_enable_shared_from_this(void *)
{
}
public:
typedef T element_type;
@ -111,7 +111,7 @@ public:
template<class Y>
explicit shared_ptr(Y * p): px(p), pn(p, checked_deleter<Y>()) // Y must be complete
{
sp_enable_shared_from_this(p);
detail::sp_enable_shared_from_this(p, p, pn);
}
//
@ -122,7 +122,7 @@ public:
template<class Y, class D> shared_ptr(Y * p, D d): px(p), pn(p, d)
{
sp_enable_shared_from_this(p);
detail::sp_enable_shared_from_this(p, p, pn);
}
// generated copy constructor, assignment, destructor are fine...
@ -179,7 +179,7 @@ public:
{
Y * tmp = r.get();
pn = detail::shared_count(r);
sp_enable_shared_from_this(tmp);
detail::sp_enable_shared_from_this(tmp, tmp, pn);
}
#endif
@ -270,7 +270,7 @@ public:
pn.swap(other.pn);
}
bool less(this_type const & rhs) const // implementation detail, never throws
bool _internal_less(this_type const & rhs) const // implementation detail, never throws
{
return pn < rhs.pn;
}
@ -316,7 +316,7 @@ template<class T> inline bool operator!=(shared_ptr<T> const & a, shared_ptr<T>
template<class T> inline bool operator<(shared_ptr<T> const & a, shared_ptr<T> const & b)
{
return a.less(b);
return a._internal_less(b);
}
template<class T> inline void swap(shared_ptr<T> & a, shared_ptr<T> & b)

View File

@ -92,7 +92,13 @@ public:
pn.swap(other.pn);
}
bool less(this_type const & rhs) const // implementation detail, never throws
void _internal_assign(T * px2, detail::shared_count const & pn2) // implementation detail
{
px = px2;
pn = pn2;
}
bool _internal_less(this_type const & rhs) const // implementation detail, never throws
{
return pn < rhs.pn;
}
@ -116,7 +122,7 @@ private:
template<class T> inline bool operator<(weak_ptr<T> const & a, weak_ptr<T> const & b)
{
return a.less(b);
return a._internal_less(b);
}
template<class T> void swap(weak_ptr<T> & a, weak_ptr<T> & b)