Boost logo

Boost :

From: David Abrahams (dave_at_[hidden])
Date: 2003-02-02 15:23:25


"David B. Held" <dheld_at_[hidden]> writes:

> "David Abrahams" <dave_at_[hidden]> wrote in message
> news:ud6mbbbcb.fsf_at_boost-consulting.com...
>> [...]
>> Borland is particularly strange about layout.
>
> Suprisingly enough, BCB 5 has maintained the optimal size throughout
> all the changes.
>
>> [...]
>> Whaaa? A temporary that never gets created?
>
> Well, I'll show you the code, and you tell me if it gets optimized away
> or not:
>
> // Inherit first
> template <class T1, class T2>
> class optimal_parents1 : public T1
> {
> // ...
>
> template <class U1, class U2>
> optimal_parents1(optimal_parents1<U1, U2> const& rhs)
> : T1(static_cast<U1 const&>(rhs))
> { U2 u2; T2 t2(u2); } // Here
>
> // ...
> };
>
> If T2(U2 const&) is empty, I would think that it wouldn't bother to
> call it in the first place. Am I missing something?

Sigh. We can't detect the presence of trivial constructors,
especially taking arbitrary arguments. What is_empty<> does is detect
classes which the EBO can potentially optimize away, i.e. those with
no data members. T2 may have a non-trivial destructor to boot.

> Maybe I shouldn't have called t2 a temporary, since it is an lvalue.
> I just meant that it's not really used for anything other than
> making sure that U2 can be converted to T2.

If that's all you care about you could just do
BOOST_STATIC_ASSERT((is_convertible<U2,T2>::value));

[you snipped the context for my question]
>> since their sole purpose is to verify policy compatibility. In the
>> majority of cases, they will simply call an appropriate copy c'tor,
>> which will be trivial or generated, because the class has no state.

>> [...]
>> Maybe you should illustrate what you mean, 'cause I'm lost.
>
> assert_check(no_check const&)
> { }
>
> This allows you to create a pointer with stricter checking from a
> pointer with no checking.

You're not showing much. I'll take your word for it.

> But no_check has no such conversion c'tors, because presumably, one
> does not want to *reduce* the level of checking. Since the checking
> policies generally don't have any state, the c'tors are all trivial,
> and hopefully, will get optimized out of existence.
> They merely serve as a compile-time check of compatibility.

I've been concerned about optimizing storage, not code. The EBO issue
has nothing to do with inlining constructors.

>> [...]
>> You could probably figure out the VC++ algorithm by
>> experimentation, but that still wouldn't help a user trying to write
>> portable, efficient code, unless you find a workaround for every
>> other compiler.
>
> Yeah, that's the problem. :( Even more disturbingly, it's not clear if
> this is just an MI problem, or a problem with inheritance in general
> with VC++. I mean, when I tried the chained policy implementation,
> it did provide the right size, but that doesn't mean it won't change if
> I update the implementation (and that version would require a lot of
> changes to get it up to speed with the MI version).

I've been saying this over and over: yes it does, for all practical
purposes. Vendors are VERY reluctant to break object code
compatibility. If they ever do break it intentionally, it will only
be to do *more* optimizations, not fewer.

-- 
                       David Abrahams
   dave_at_[hidden] * http://www.boost-consulting.com
Boost support, enhancements, training, and commercial distribution

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk