Запись таблицы виртуальных функций из класса, который не связан

Я просматриваю VFT (VMT) простой программы на C++ для Windows (у меня нет исходного кода, только бинарный), скомпилированной Visual Studio с некоторой оптимизацией.

Я заметил, что использует наследование и полиморфизм. Я нашел расположение структуры s_RTTIBaseClassArray для каждого класса, который есть в программе. В этом месте есть массив указателей на структуру _s_RTTIBaseClassDescriptor, Массив дескрипторов базовых классов должен предоставлять вам информацию обо всех классах, из которых получен текущий класс.

Таблица виртуальных функций (метод) - это таблица, которая содержит указатели на все виртуальные функции текущего класса. Однако в VFT нескольких классов я нашел указатель на виртуальный метод, который на самом деле принадлежит другому классу, который (согласно массиву базового класса) не связан с текущим классом. Пример ниже:

ClassA_BaseClassArray:
            dd offset ClassA_BaseClassDescriptor
            dd offset ClassB_BaseClassDescriptor ; ClassA inherits from ClassB

ClassB_BaseClassArray:
            dd offset ClassB_BaseClassDescriptor

ClassC_BaseClassArray:
            dd offset ClassC_BaseClassDescriptor

ClassA_VMT: 
            dd offset ClassA_VM1 ; virtual method of ClassA
            dd offset ClassA_VM2
            dd offset ClassB_VM2 ; virtual method of ClassB - override
            dd offset ClassC_VM3 ; virtual method of ClassC - NOTHING TO DO HERE
            dd offset ClassA_VM3

Пример короткий, в реальных классах гораздо больше виртуальных методов.

После осмотра ClassC_VM3 Я заметил, что он состоит всего из двух инструкций:

mov    eax, [ecx+10h]
retn

До сих пор я нашел около 3 VMT, похожих на этот пример, несвязанный метод всегда такой короткий.

Мой вопрос: что это вызывает? Может ли код ClassC_VM3 быть идентичным коду некоторых ClassA метод, так что компилятор просто оптимизировал его?

1 ответ

Решение

Это может быть вызвано свертыванием COMDAT, оптимизацией, которая объединяет функции с одинаковым точным машинным кодом в одну. Поскольку это такая простая функция, шансы на это хорошие.

Другие вопросы по тегам