[C++-sig] Bug and patch for boost.python with enable_shared_from_this

Ralf W. Grosse-Kunstleve rwgk at yahoo.com
Tue Feb 12 00:55:06 CET 2008


Thanks for the patch! I'd love to check this in for you, but for the
change in shared_ptr.hpp you'll need Peter Dimov's approval, and the
shared_ptr documentation would have to be updated. Also, your reproducer
should be turned into a unit test (in boost/libs/python/test).

Is there any chance that the shared_ptr patch could somehow be avoided?

Ralf

----- Original Message ----
From: Chad Austin <chad at imvu.com>
To: c++-sig at python.org
Sent: Sunday, February 10, 2008 5:14:45 PM
Subject: [C++-sig] Bug and patch for boost.python with enable_shared_from_this


Hi all,

A month ago or so we discovered a bug in Boost.Python
that manifests when using enable_shared_from_this.  Here is a test case
that demonstrates the bug:


#include <boost/python.hpp>

#include <boost/enable_shared_from_this.hpp>



using namespace boost;

using namespace boost::python;



class Test;

typedef shared_ptr<Test> TestPtr;



class Test : public enable_shared_from_this<Test> {

public:

    static TestPtr construct() {

        return TestPtr(new Test);

    }



    void act() {

        TestPtr kungFuDeathGrip(shared_from_this());

    }



    void take(TestPtr t) {

    }

};



void Export_test() {

    class_<Test, TestPtr, noncopyable>("Test")

        .def("construct", &Test::construct)

        .staticmethod("construct")



        .def("act", &Test::act)

        .def("take", &Test::take)

        ;

}





And here is the Python:



        x = Test.construct()

        x.take(x)

        x.act()



The bug (as I understand it) is that the shared_ptr_from_python
converter creates a new shared_ptr for the Test instance to pass it
into C++.  This new shared_ptr has a nop deleter, except that it keeps
the Python object alive as long as the new shared_ptr is alive.  The
problem here is that creating a shared_ptr to an object of type T when
T is enable_shared_from_this<T> resets the weak pointer inside of
enable_shared_from_this<T>.  (See shared_ptr's constructors for
the details of the implementation.)  A fix that passes the test above
and has worked for us is to change shared_ptr's constructor to accept a
dont_enable_shared_from_this argument and pass that in from the
shared_ptr_from_python converter.  The patch is attached (against boost
1.33, but the bug didn't look fixed in 1.34 either).


Cheers,
Chad

p.s. I have seen other people with this problem as well.  Googling for bad_weak_ptr turns up several results.



-----Inline Attachment Follows-----

_______________________________________________
C++-sig 
mailing 
list
C++-sig at python.org
http://mail.python.org/mailman/listinfo/c++-sig




-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/cplusplus-sig/attachments/20080211/264e9469/attachment.htm>


More information about the Cplusplus-sig mailing list