I've manage to narrow down what the
problem is and created a test case that simulates my real code.
The problem occurs in a destructor (of
B1) when it tries to get a shared pointer to shared_from_this() from its
base class (base_class). I think that the execution of the
destructor hierarchy has deleted the original shared_ptr to B2 meaning
that the shared_from_this() returns an error (because shared_from_this()
requires that the object is managed by a shared_ptr).
My original destructor code was using
raw pointers (ie. this) which worked fine because the base_class destructor
was last to be called and was still alive at the time when ~B2() is called.
This seems like it could be a limitation of boost::shared_ptr?
I have placed my code in the destructor
of B2 because in my program I am never sure exactly of the lifespan of
B2. During execution I accumulate information in the B2 object and
then write out this information at the end of its lifespan i.e in the destructor.
I'm open to any ideas including any
ways that I might be able to restructure my program.
#include <boost/smart_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
#include <boost/scoped_ptr.hpp>
#include <iostream>
class base_class : public boost::enable_shared_from_this<base_class>
{
private:
boost::shared_ptr<base_class>
m_Linked;
// link to another base_class
public:
base_class(){};
base_class(
boost::shared_ptr<base_class> pLinked)
{
m_Linked = pLinked;
// store link to other base class
}
};
class B : public base_class
{
public:
B(boost::shared_ptr<base_class>
pLinked) : base_class( pLinked){}
};
class B1 : public B
{
public:
B1(boost::shared_ptr<base_class>
pLinked) : B( pLinked){}
~B1()
{
try{
boost::shared_ptr<base_class>
ptr_This = shared_from_this();
// Exception occurs here
// Write
out some links here.
}
catch (exception &e)
{
std::cout
<< e.what();
}
}
};
class B2 : public B1
{
public:
B2(boost::shared_ptr<base_class>
pLinked) : B1( pLinked){}
};
class A : public base_class
{
public:
A()
: base_class(){};
int
f;
void
Process()
{
boost::shared_ptr<base_class> ptr_me
= shared_from_this();
// get pointer to myself
//afterwards
- use_count = 2, weak_count = 2
f = 3;
if (f == 3){
boost::shared_ptr<B2>
ptr_b2( new B2(ptr_me) ) ;
// create new
B2 and pass pointer to me.
}else{
//
crashes with bad_weak_ptr error on this line.
}
}
};
void main()
{
boost::shared_ptr<A>
ptr_a( new A() );
ptr_a->Process();
}
// EOF