[cxx-abi-dev] std::type_info::hash_code/before

Richard Smith richardsmith at googlers.com
Tue Oct 4 22:48:00 UTC 2016


On 4 October 2016 at 15:29, John McCall <rjmccall at apple.com> wrote:

> On Oct 4, 2016, at 3:19 PM, Richard Smith <richardsmith at googlers.com>
> wrote:
> On 4 October 2016 at 14:54, John McCall <rjmccall at apple.com> wrote:
>
>>
>> On Oct 4, 2016, at 2:11 PM, Richard Smith <richardsmith at googlers.com>
>> wrote:
>>
>> On 4 October 2016 at 13:22, John McCall <rjmccall at apple.com> wrote:
>>
>>> > On Oct 4, 2016, at 4:25 AM, David Vandevoorde <daveed at edg.com> wrote:
>>> > Shouldn't the ABI document specify how type_info entries are collated
>>> and hashed with their before() and hash_code() members?
>>>
>>> Yes, that seems reasonable.  It's only necessary for interoperation of
>>> multiple standard libraries on a platform, but that's a thing.
>>>
>>> Since the ABI only formally guarantees that the names are uniqued, I
>>> think the obviously correct way of implementing these is to compare name
>>> pointers in before() and reinterpret the name pointer as the result of
>>> hash_code().  That is what libc++ seems to do.  I don't have a recent
>>> libstdc++ header around; the ancient one I do have uses that rule for
>>> before() and doesn't implement hash_code(), but IIRC these days libstdc++
>>> uses a variant ABI for type_info anyway.
>>>
>>
>> libstdc++ has two modes: in one mode, it guarantees typeinfo name
>> uniqueness across the program, uses the pointer for before(), and
>> reinterprets the pointer as a hash for hash_code. In the other mode (where
>> they try to merge types from a .so even if it was dlopen'd RTLD_LOCAL [1]),
>> some names are unique and others are not; hash_code computes a hash of the
>> name, and before ... well, before is broken, and doesn't produce a strict
>> weak order.
>>
>>
>> Is this set by environment variable or by #define?  I suppose the latter
>> would technically work if done consistently enough in program code to paper
>> over the ODR problems, since the parts of the ABI library that do type_info
>> comparisons (for dynamic_cast and exceptions) are unlikely to use either
>> before() or hash_code().
>>
>
> It looks like it's a libsupc++ configure-time #define.
>
>
> Ah, so basically a platform decision, then.  Although I guess it's
> probably more plausible to swap in your own libsupc++ on Linux than it
> would be on Darwin.
>
>  [1]: It would seem reasonable for the ABI document to say something about
>> what happens in this case. If I understand correctly, the issue is that a
>> .so that's dlopen'd RTLD_LOCAL can contain a weak definition of the
>> type_info for a type that's logically part of another library, and if it's
>> loaded before that other library is, the type_info name doesn't get merged
>> despite there being some intent that it's the same type.
>>
>>
>> I suppose I can't just say that that's an ELF problem. :)
>>
>> What we did for ARM64 seems like the right basic approach: the type_info
>> object records whether it's unique or non-unique, and non-unique RTTI just
>> falls back on string-based comparisons / hashes.  The type_info is unique
>> if and only if it's for a fundamental type in the ABI library or a
>> polymorphic class with a key function.
>>
>
> That's approximately what GCC does. IIRC, you guys use a tag bit for the
> local/non-local choice, whereas GCC prepends the name with '*' for the case
> where a pointer comparison is applicable. The tag bit approach seems
> substantially better, since it doesn't require first fetching through the
> pointer in order to tell that we didn't actually need to fetch through the
> pointer :)
>
>
> Yep, that's why we did it that way. :)
>
> Does GCC just always emit unique RTTI with the '*' prefix, or does it rely
> on being configured the same way as libsupc++?
>

It looks like it unconditionally emits the '*' for any class that is not
accessible from outside the translation unit. (The presence or absence of a
key function doesn't seem to make any difference.)

> On the other hand, GCC has a trick you don't mention here: it also treats
> internal-linkage types has having unique type_info.
>
>
> Oh, yes, we do that as well.
>
> John.
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://sourcerytools.com/pipermail/cxx-abi-dev/attachments/20161004/6e65b2b6/attachment-0001.html>


More information about the cxx-abi-dev mailing list