[cfe-dev] Could we emit inline virtual member functions as available_externally when there's a key function (same as vtable and debug info)?

David Blaikie via cfe-dev cfe-dev at lists.llvm.org
Wed Jun 15 10:27:08 PDT 2016


On Wed, Jun 15, 2016 at 9:01 AM, Reid Kleckner <rnk at google.com> wrote:

> On Tue, Jun 14, 2016 at 12:51 PM, David Blaikie via cfe-dev <
> cfe-dev at lists.llvm.org> wrote:
>
>> On Sat, Jun 4, 2016 at 9:36 AM, Piotr Padlewski <
>> piotr.padlewski at gmail.com> wrote:
>>
>>> Sorry, my bad - there was a problem with available_externally vtables
>>> that we were unable to generate when there was a inline virtual function.
>>>
>>
>> Ah, I've found the code and some of the comments for that - do you
>> remember the details or have pointers to the related threads/reviews/etc
>> that came to that conclusion?
>>
>> Could we not emit the inline functions as linkonce_odr as usual and then
>> emit the available_externally vtable on top of that. Presumably once we do
>> all the optimization and drop the vtable, any of these inline virtual
>> functions that haven't got any devirtualized calls to them will disappear
>> due to lacking any reference holding them alive.
>>
>> It'd bloat object files a bit, but only in the cases where there's an
>> optimization win - right?
>>
>> But I guess there's a reason that doesn't work/wasn't implemented.
>>
>
> It's complicated. Here's an interesting test case where it is hard to
> generate an available_externally vtable for C:
>
> #include <memory>
> struct A;
> struct B {
>   virtual void ~B();
> };
> struct C : B {
>   C();
>   virtual void f();
>   std::unique_ptr<A> a;
> };
> C *getit() {
>   C *p = new C;
>   p->f();
>   return p;
> }
>
> In order to emit an externally_available vtable, we need to emit all the
> inline virtual functions as linkonce_odr, which requires semantically
> checking them up front, which would implicitly define ~C, which would
> instantiate ~unique_ptr<A>, which requires A to be complete.
>
> The question is, are we allowed to require 'A' to be a complete type so
> that we can emit the implicit definition of C::~C?
>
> Blink/WebKit/Nico want the answer to be "no", and most compilers give that
> answer, because there is no vtable reference required here to generate
> code. Richard's interpretation of the standard says that the call to the
> virtual function 'f' allows us to do the semantic checking, so we could
> change our minds if we think it's worth the hassle of compatibility issues
> and user confusion.
>
> I think it will be very hard to explain to users why 'A' needs to be
> complete, since there's no clear vtable reference. We would need a
> diagnostic note saying that the vtable was required to be complete at this
> virtual call to support devirtualization.
>

Well, alternatively we can meet in the middle & not apply this rule to
implicit virtual functions (the dtor being the only possible instance of
that, I think) if that's especially convenient/valuable.

Also, for now, I don't think we emit the available_externally vtable when
the ctor is out of line anyway (we only emit it when we emit the store of
the vtable pointer - in theory we could emit it elsewhere and use
llvm.assume after the ctor call to indicate that the vtable pointer does
now point to the vtable in question)

- Dave
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20160615/7350f437/attachment.html>


More information about the cfe-dev mailing list