[C++-sig] Py++: Memory Ownership Passing

Anand, Kumar kanand at qualcomm.com
Thu Feb 22 04:06:04 CET 2007


Thanks! Registering the implicit converter worked. I am now able to
transfer the ownership of Derived class object from python to C++ via an
interface that takes a Base class pointer. 

 

Gustavo, please see the following complete code snippet. 

 

1) Exposed class 'Base' as follows:

           bp::class_< Base,  std::auto_ptr< Base > > ("Base" )

               .def( bp::init< >() ); 

 

2) Exposed class 'Derived' as follows:

           bp::class_< Derived, bp::bases< Base >, std::auto_ptr<Derived
> > ("Derived" )

               .def( bp::init< >() );

    

3) Register the implicit converter

     boost::python::implicitly_convertible< std::auto_ptr< Derived >,
std::auto_ptr< Base > >();

 

4) Now assuming you have a 'func' function that takes a 'Base*' as
argument and takes ownership of the object passed. And you want to
expose this to python.

    i.e. void func (Base* ptr);

 

Exposing the above function as it is, would not work because the object
referred by ptr would be deleted twice (once in C++ inside 'func' and
finally by Python Interpreter again). To pass the memory ownership from
python to C++ and avoid double deletion, create the func_wrapper as
follows and expose it to python as 'func'

 

          void func_wrapper (std::auto_ptr<Base> b)

          {

                   func.(b.get());

                   b.release() // IMPORTANT !!!

           }

 

Thanks

Kumar

________________________________

From: c++-sig-bounces at python.org [mailto:c++-sig-bounces at python.org] On
Behalf Of Gustavo Carneiro
Sent: Wednesday, February 21, 2007 2:45 PM
To: Development of Python/C++ integration
Subject: Re: [C++-sig] Py++: Memory Ownership Passing

 

On 2/21/07, Anand, Kumar <kanand at qualcomm.com> wrote:

	Ok, I have tried the following but it doesn't work.
	
	1) Exposed class 'Base' as follows:
	           bp::class_< Base,  std::auto_ptr< Base > > ("Base" )
	               .def( bp::init< >() ); 
	1) Exposed class 'Derived' as follows:
	           bp::class_< Derived, bp::bases< Base >,
std::auto_ptr<
	Derived > > ("Derived" )
	               .def( bp::init< >() ); 
	2) Created the func_wrapper as follows and exposed it to python
as
	'func'
	          Void func_wrapper (std::auto_ptr<Base> b)
	          {
	                   func.(b.get());
	                   b.release()
	           }
	
	Now In Python when I do this:
	import Boost_Test
	d = Boost_Test.Derived()
	Boost_Test.func(d);
	
	Above code throws an error because of C++ signature mismatch. I
am
	trying to pass a std::auto_ptr<Derived>to a std::auto_ptr<Base>.
How to 
	solve this problem?


  In Py++ code I think it's something like this:

     mb.class_('Base').add_registration_code(
        "boost::python::implicitly_convertible<"
        " std::auto_ptr< Derived >," 
        " std::auto_ptr< Base > >();", False)

  However, if you have the same problem as I do then you will find out
that all these std::auto_ptr hacks will not solve the memory error in
the end.  I have been trying to solve the exact same problem for a few
days now... :-( 


-- 
Gustavo J. A. M. Carneiro
"The universe is always one step beyond logic." 

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


More information about the Cplusplus-sig mailing list