С++, что может сделать type_info::hash_code различающимся для двух (предположительно) одинаковых объектов

После попытки отладить неудачное динамическое преобразование вниз, я в конце концов обнаружил, что причина, вероятно, заключается в следующем: type_info::hash_code для типа, к которому он приводится, отличается в зависимости от того, где в коде он вызывается. Однако type_info::name остается точно таким же. К сожалению, я не могу воспроизвести поведение в минимальном примере, поскольку оно появляется в довольно запутанном контексте. Поэтому я, по сути, ищу ключи к разгадке того, что может быть причиной такого поведения, и, следовательно, в каком направлении я могу решить эту проблему.

Короче говоря, если это связано, тип выглядит так (ОТРЕДАКТИРОВАНО):

class A {...}

template < template <class> class>
class B : virtual public A {...}

template < template <class> class>
class C : virtual public A {...}

template < template <class> class>
class D : public B, public C {...}

template <class>
class E {...}

Проблема выглядит так:

D<E>* d = build_d();    
B<E>* b = d; 
A* a = d;     

dynamic_cast<D<E>*>(b);//returns correct pointer
dynamic_cast<D<E>*>(a);//returns 0, and really shouldn't !!

typeid(B<E>).hash_code();//differing depending where in the code this is called

Вызовы type_info::hash_code выполняются внутри разных библиотек (моих собственных). Покопавшись, я нашел опцию компилятора -rdynamic с GCC (даже если я использую Clang). Я не уверен, что это может быть как-то связано с моей проблемой.


РЕДАКТИРОВАТЬ: В конце концов я нашел хорошую подсказку. К сожалению, пока нет решения. Похоже, проблема может быть связана с Qt в конце.

Проблема возникает в функции слота. Когда слот вызывается сигналом, нисходящее приведение dynamic_cast не выполняется. Но если вместо этого я вручную вызову слот (например, в main), он преуспеет. И если вручную вызывать слот, то запускать его по сигналу, тоже получается. Аргумента для сигнала нет, а содержимое слота "нейтрализовано" и не зависит ни от каких параметров. На 99,99% уверен, что проблема не в ошибке алгоритма распределения.

Похоже qt_static_metacall при вызове слота как-то теряет след свойств приведения. Может ли иметь к этому какое-то отношение тот факт, что предварительно скомпилированный связанный moc?


person brahmin    schedule 10.06.2015    source источник