blockchain187
blockchain187

Reputation: 59

Why does the gtest death test loop indefinitely

In my project we imitate blockbox testing using gtest. For that reason we implemented a mockMain() function containing all relevant code that should be inside the blackbox. Then we use the TEST_F functions by gtest to execute that main and verify the output it generates. The problem now is: I want to write death tests because for some input made, the program should exit. Unfortunately, the death test loops indefinitely, when I execute it. Since the actual program is enormous, I tried to capture the essence of what is happening in the following code. It has the same problem as the main program.

I found out on Windows the deathtests are executed int the "threadsafe" mode, which reruns the whole program. Is there a way to change that?

main.cpp

bool runBlackboxTest = true;

int main(int argc, char *argv[])
{   //Only execute tests if flag is enabled
    if(runBlackboxTest){
        RectangleBlackboxTest::runAllTests();
        exit(0);
    }
    Rectangle oneRect(12.1, 7.4);
    std::cout << "Area: " << oneRect.getArea() << std::endl;
    return 0;
}

Rectangle.cpp

Rectangle::Rectangle(double a, double b){
    this->side_a = a;
    this->side_b = b;

    this->area = a*b;
}

double Rectangle::getArea(){
    return this->area;
}

double Rectangle::rectExit(){
    std::cout << "Exiting program." << std::endl;
    exit(1); 
    return 0;
}

RectangleBlackboxTest.cpp

using RectangleBlackboxDeathTest = RectangleBlackboxTest;

int RectangleBlackboxTest::runAllTests(){
    testing::InitGoogleTest();
    return RUN_ALL_TESTS();
}

//Just some example functinoality
void RectangleBlackboxTest::mockMain(){
    double a, b;
    srand(time(NULL));
    a = double(rand() % 100 + 1) / 17;
    b = double(rand() % 100 + 1) / 11;
    this->testingRect = new Rectangle(a, b);
    std::cout << "a: " << a << " b: " << b << " Area: " << this->testingRect->getArea() << std::endl;
}

//Imitating an exit in the mockMain()
void RectangleBlackboxTest::mockMainWithExit(){
    this->mockMain();
    this->testingRect->rectExit();
}

void RectangleBlackboxTest::TearDown(){
    delete this->testingRect;
}

//This is the part that loops indefinitely
TEST_F(RectangleBlackboxDeathTest, firstDeathTest){
    EXPECT_EXIT(mockMainWithExit(), testing::ExitedWithCode(1), ".*");
}

Upvotes: 1

Views: 527

Answers (1)

blockchain187
blockchain187

Reputation: 59

For anyone having the same problem:

The main problem lies in testing::InitGoogleTest().

When gtest finds a death test, it creates a new process using createProcessA(...) under Windows and passes additional parameters, to make sure the child process only executes the current death test. This leads to problems, when those parameters are not given to testing::InitGoogleTest() in the child process. In this case it doesn't receive the information to only execute the death test and starts running the whole test code again, leading to recursion.

TLDR:

Pass the command line arguments from main(int argc, char *argv[]) to testing::InitGoogleTest():

testing::InitGoogleTest(argc, argv)

Upvotes: 2

Related Questions