[C++-sig] Protected destructor compile error

Allen Bierbaum abierbaum at gmail.com
Fri Jun 23 20:29:28 CEST 2006


On 6/22/06, David Abrahams <dave at boost-consulting.com> wrote:
> "Allen Bierbaum" <abierbaum at gmail.com> writes:
>
> > One additional question: Is there any metafunction (something like
> > pointee<>) that could be specialized to tell boost.python that when
> > it sees a const& of this type it should not assume that it can make
> > a temporary?  In effect some way to tell it to choose to use the
> > path that the thin wrapper would use instead.
> >
> > If there isn't a metafunction like this, would it be difficult to
> > nimplement something like this?
>
> I think the answer to both questions is no.  It sounds like a
> reasonable thing to do, though.
>
> > (if not, I am willing to work on it if you give me some direction on
> > where to look and what to look for) To help with cases like mine, it
> > would be nice to make the default version use type traits to detect
> > if the type has a public destructor (and anything else it needs to
> > make the temporary).
>
> It's not possible to detect that, unfortunately.

It would not be possible to do in C++, but it would be possible to
have a code generator like pyplusplus detect this case and
automatically set some metafunction/flag/whatever to tell the system
that it can't destruct the type so it should not allow creation of a
temporary.

Now that I think about my case it more detail I am starting to wonder
if there is a problem with the API I a binding.
For example the reason this method:

bool Camera::calcViewRay (Line &line, Int32 x, Int32 y, const Viewport &port);


is not working is because Viewport objects are only supposed to be
handled using ViewportPtrs (custom ref-counted shared pointer).  Since
they are not handled this way in this case it causes these problems.

This API would cause problems even in pure C++ code if someone passed
in an object of another type that is implicitly convertible to a
Viewport.  If Viewport had a constructor that took an std::string for
example and they tried to pass that in C++ would attempt to create a
temporary behind the scenes and have the same problem at compile time.
 So I guess this is a case of valid (but possibly questionable) C++
that boost.python fails to wrap by default.  (I should note that in my
case the API does not allow implicit conversion to Viewport or any of
the other types that have protected destructors.  They are all created
only by calling a static creation method that returns a smart ptr.)

It is worth mentioning that the other methods where this is a problem
in the current library I am binding are things like
operator==(const&), operator<(const&), and operator!=(const&).

> And _making_ the
> temporary is a completely separate issue from destroying it.  The part
> of the converter that makes the temporary is looked up dynamically
> based on the source Python type and in this case of course, nothing is
> ever found.  The fact that the destruction code is instantiated
> unconditionally by the static part of the is really a sort of
> optimization.
>
> The simplest way to make this work for everyone would be to make the
> dynamic part of the converter responsible for destroying the
> temporary.  That would make your case work without the need for any
> traits.  However, there's a tradeoff; there would be an extra function
> pointer indirection, at least.  In the case of converting to a C++
> type with a trivial destructor, that no-op call through a function
> pointer would replace an "inline no-op" (i.e., nothing at all).  Other
> minor costs include storage for that function pointer.
>
> Also there's the issue that this would cause a hard incompatibility
> with extension modules built against an earlier Boost.Python (their
> dynamic converters don't supply that destruction code).
>
> Did I mention I'm not making any heavy decisions while I'm on
> vacation?  Why don't y'all discuss the tradeoffs here and decide
> whether it's worth it.

Has anyone else ever ran into this problem?  If not, then maybe it is
not worth the effort and performance cost to try to fix generically.
I could always just try to make some smart wrapper code with
pyplusplus that automatically detects this case and creates a thin
wrapper for me.  (any ideas here Roman?)

David: Thanks for replying while on vacation.  I wouldn't even be
reading my e-mail if I was on vacation. :)

-Allen

> --
> Dave Abrahams
> Boost Consulting
> www.boost-consulting.com
>
> _______________________________________________
> C++-sig mailing list
> C++-sig at python.org
> http://mail.python.org/mailman/listinfo/c++-sig
>



More information about the Cplusplus-sig mailing list