Google Mock: при выходе из программы обнаружен протекший макет?
Когда я определяю свой тест следующим образом, он работает.
TEST(MyService, WhenCalled_DoesTheRightThingTM) {
// Arrange
ThirdPartyClassFake stub;
EXPECT_CALL(stub, GetFirstName())
.WillRepeatedly(Return("Bob"));
// Act
std::string result = stub.GetFirstName();
// Assert
EXPECT_STREQ("Bob", result);
}
ThirdPartyClassFake - это созданный мною класс Google.
Когда я добавляю код, который передает указатель на мою заглушку в класс-оболочку, я получаю утечку памяти:
TEST(MyService, WhenCalled_DoesTheRightThingTM) {
// Arrange
ThirdPartyClassFake stub;
EXPECT_CALL(stub, GetFirstName())
.WillRepeatedly(Return("Bob"));
// Act
MyWrapperClass wrapper(&stub);
std::string result = stub.GetFirstName();
// Assert
EXPECT_STREQ("Bob", result);
}
Ошибка:
1> [ RUN ] MyService.WhenCalled_DoesTheRightThingTM
1>unknown file : error : SEH exception with code 0xc0000005 thrown in the test body.
1> [ FAILED ] MyService.WhenCalled_DoesTheRightThingTM (1 ms)
1>c:\myfile.cpp(17): error : this mock object (used in test
MyService.WhenCalled_DoesTheRightThingTM) should be deleted but never is.
Its address is @0028E40C.
1>EXEC : error : 1 leaked mock object found at program exit.
1>C:\Program Files (x86)\MSBuild\Microsoft.Cpp\v4.0\Microsoft.CppCommon.targets(113,5):
error MSB3073: The command "C:\MyProject.Tests.exe
1>C:\Program Files (x86)\MSBuild\Microsoft.Cpp\v4.0\Microsoft.CppCommon.targets(113,5):
error MSB3073: :VCEnd" exited with code 1.
Не уверен, что это актуально, но я должен добавить, что ThirdPartyClassFake
подклассы из стороннего абстрактного класса (который я не могу контролировать) со всеми виртуальными методами, но без виртуального деструктора. Также он объявлен с атрибутом Microsoft __declspec(novtable)
,
Я думал, что проблема может быть в отсутствии виртуального деструктора, как описано в FAQ по Google Mock. Однако я полагаю, что если бы это было проблемой, то первое испытание тоже должно было пройти.
Как я могу исправить / обойти эту ошибку?
2 ответа
0xc0000005 - нарушение прав доступа из памяти. Вероятно, это исключение SEH было сгенерировано, и деструктор не был вызван должным образом, если вы не скомпилировали код с правильными переключателями.
Я думаю, что проследил ошибку до деструктора MyWrapperClass
которая вызывает глобальную / статическую функцию Destroy
(Третье лицо) на объекте, переданном в конструктор. Поскольку объект, который я передаю, является подделкой, он, вероятно, вызывает Destroy
потерпеть неудачу по той или иной причине. Так что вопрос в том, как мне обойти это? В этом случае, MyWrapperClass
это тестируемый объект, поэтому я не хочу изменять его или макетировать. Я думаю, я должен найти способ издеваться над функцией Destroy
, Отзовусь, если узнаю как.