~ps-jenkins/compiz/latestsnapshot-10.9.10+13.10.20131011-0ubuntu1

« back to all changes in this revision

Viewing changes to cmake/src/compiz/compiz_discover_gtest_tests.cpp

Added compiz_discover_tests.

gtest_add_tests is good for the basic Google Test usage, but its source
based scanning falls short in a couple of areas - namely it requires that
there be no space between TEST* and ( and it also does not work for templated
tests.

compiz_discover_tests builds a small C++ program to parse the output
of --gtest_list_tests and adds those at make-time to the CTestTestfile.cmake
in the current binary directory. This allows us to correctly introspect the test
binary and get /all/ the tests regardless of the source file.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#include <map>
 
2
#include <vector>
 
3
#include <string>
 
4
#include <istream>
 
5
#include <ostream>
 
6
#include <fstream>
 
7
#include <iterator>
 
8
#include <iostream>
 
9
#include <libgen.h>
 
10
 
 
11
int main (int argc, char **argv)
 
12
{
 
13
    std::cin >> std::noskipws;
 
14
 
 
15
    if (argc < 2)
 
16
    {
 
17
        std::cout << "Usage: PATH_TO_TEST_BINARY --gtest_list_tests | ./build_test_cases PATH_TO_TEST_BINARY";
 
18
        return 1;
 
19
    }
 
20
 
 
21
    std::map<std::string, std::vector<std::string> > testCases;
 
22
    std::string line;
 
23
    std::string currentTestCase;
 
24
 
 
25
    while (std::getline (std::cin, line))
 
26
    {
 
27
        /* Is test case */
 
28
        if (line.find ("  ") == 0)
 
29
            testCases[currentTestCase].push_back (currentTestCase + line.substr (2));
 
30
        else
 
31
            currentTestCase = line;
 
32
 
 
33
    }
 
34
 
 
35
    std::ofstream testfilecmake;
 
36
    char *base = basename (argv[1]);
 
37
    std::string   gtestName (base);
 
38
 
 
39
    testfilecmake.open (std::string (gtestName  + "_test.cmake").c_str (), std::ios::out | std::ios::trunc);
 
40
 
 
41
    if (testfilecmake.is_open ())
 
42
    {
 
43
        for (std::map <std::string, std::vector<std::string> >::iterator it = testCases.begin ();
 
44
             it != testCases.end (); it++)
 
45
        {
 
46
            for (std::vector <std::string>::iterator jt = it->second.begin ();
 
47
                 jt != it->second.end (); jt++)
 
48
            {
 
49
                if (testfilecmake.good ())
 
50
                {
 
51
                    std::string addTest ("ADD_TEST (");
 
52
                    std::string testExec (" \"" + std::string (argv[1]) + "\"");
 
53
                    std::string gTestFilter ("\"--gtest_filter=\"");
 
54
                    std::string filterBegin ("\"");
 
55
                    std::string filterEnd ("\")");
 
56
 
 
57
                    testfilecmake << addTest << *jt << testExec << gTestFilter << filterBegin << *jt << filterEnd << std::endl;
 
58
                }
 
59
            }
 
60
        }
 
61
 
 
62
        testfilecmake.close ();
 
63
    }
 
64
 
 
65
    std::ifstream CTestTestfile ("CTestTestfile.cmake", std::ifstream::in);
 
66
    bool needsInclude = true;
 
67
    line.clear ();
 
68
 
 
69
    std::string includeLine = std::string ("INCLUDE (") +
 
70
                              gtestName  +
 
71
                              std::string ("_test.cmake)");
 
72
 
 
73
    if (CTestTestfile.is_open ())
 
74
    {
 
75
        while (CTestTestfile.good ())
 
76
        {
 
77
            std::getline (CTestTestfile, line);
 
78
 
 
79
            if (line == includeLine)
 
80
                needsInclude = false;
 
81
        }
 
82
 
 
83
        CTestTestfile.close ();
 
84
    }
 
85
 
 
86
    if (needsInclude)
 
87
    {
 
88
        std::ofstream CTestTestfileW ("CTestTestfile.cmake", std::ofstream::app | std::ofstream::out);
 
89
 
 
90
        if (CTestTestfileW.is_open ())
 
91
        {
 
92
            CTestTestfileW << includeLine;
 
93
            CTestTestfileW.close ();
 
94
        }
 
95
    }
 
96
 
 
97
    return 0;
 
98
}