Reputation: 31
I'm trying to include files from one directory (/source) into test cases in another (/test) but cmake is unable to find any of the files in /source.
The structure of my project:
PrettyDD/
+ CMakeLists.txt
+ external/
+ CMakeLists.txt
+ gmock-1.7.0/
+ source/
+ CMakeLists.txt
+ parser.cpp
+ parser.h
+ main.cpp
+ ...
+ test/
+ CMakeLists.txt
+ test1.cpp
The error message:
marcus@lean-machine:~/Programming/PrettyDD/build$ cmake ../ -DCMAKE_BUILD_TYPE=Debug -G "CodeBlocks - Unix Makefiles"
-- Could NOT find Threads (missing: Threads_FOUND)
-- Could NOT find Threads (missing: Threads_FOUND)
-- Configuring done
CMake Error at test/CMakeLists.txt:12 (add_executable):
Cannot find source file:
parser.cpp
Tried extensions .c .C .c++ .cc .cpp .cxx .m .M .mm .h .hh .h++ .hm .hpp
.hxx .in .txx
/test/CMakeLists.txt
:
set(GMOCK_DIR "${CMAKE_SOURCE_DIR}/external/gmock-1.7.0"
CACHE PATH "The path to the GoogleMock test framework.")
set_property(TARGET gtest APPEND_STRING PROPERTY COMPILE_FLAGS " -w")
include_directories(SYSTEM ${GMOCK_DIR}/gtest/include
${GMOCK_DIR}/include)
include_directories(SYSTEM "${PROJECT_SOURCE_DIR}/source")
function(add_gmock_test target)
add_executable(${target} ${ARGN})
target_link_libraries(${target} gmock_main)
add_test(${target} ${target})
add_custom_command(TARGET ${target}
POST_BUILD
COMMAND ${target}
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
COMMENT "Running ${target}" VERBATIM)
endfunction()
add_gmock_test(tests test1.cpp parser.cpp)
I have verified that ${PROJECT_SOURCE_DIR}/source
points to the right directory by use of CMake's message()
.
If I explicitly specify the path to parser.cpp
(../source/parser.cpp
) in add_gmock_test()
then it's able to find the file.
I can also successfully run the test if I first build a library out of parser.cpp
(and it's dependencies) in /source/CMakeLists.txt
and add it where I link gmock_main
.
Why can't CMake find parse.cpp
or any other file in /source
? What am I doing wrong?
Leaving parser.cpp
out of add_gmock_test(tests test1.cpp)
gives me the following error:
marcus@lean-machine:~/Programming/PrettyDD/build$ make
[ 55%] Built target PrettyDD
[ 66%] Built target gmock
[ 83%] Built target gmock_main
[ 88%] Built target gtest
[ 94%] Built target gtest_main
Linking CXX executable tests
CMakeFiles/tests.dir/test1.cpp.o: In function `Parser_Construct_Test::TestBody()':
/home/marcus/Programming/PrettyDD/test/test1.cpp:7: undefined reference to `Parser::Parser()'
collect2: error: ld returned 1 exit status
test/CMakeFiles/tests.dir/build.make:86: recipe for target 'test/tests' failed
make[2]: *** [test/tests] Error 1
CMakeFiles/Makefile2:316: recipe for target 'test/CMakeFiles/tests.dir/all' failed
make[1]: *** [test/CMakeFiles/tests.dir/all] Error 2
Makefile:86: recipe for target 'all' failed
make: *** [all] Error 2
This is what test1.cpp
looks like:
#include <gmock/gmock.h>
#include <gtest/gtest.h>
#include "parser.h"
TEST(Parser, Construct) {
Parser parser;
}
parser.cpp
:s constructor:
Parser::Parser() {
createFunctionMap();
}
declared in parser.h
as:
class Parser {
public:
Parser();
...
There should be nothing wrong with the constructor as the program itself runs fine. So why am I getting this error?
Upvotes: 3
Views: 10205
Reputation: 381
include_directories() only changes the compiler parameters for include directories, that means you can include "parser.h" somewhere in your test code using
#include "parser.h"
and .../PrettyDD/source is searched for this file.
I do not think parser.cpp contains test code. So it should not be part of your test project:
add_gmock_test(tests test1.cpp)
Should be enough. Otherwise you should rethink your project structure.
Alternatively you can also use:
add_gmock_test(tests test1.cpp ../source/parser.cpp)
EDIT:
Regarding the question in the comments. Nearly every cmake commands' parameter is either relative to ${CMAKE_CURRENT_SOURCE_DIR} or ${CMAKE_CURRENT_BINARY_DIR}. As far as I know there is no "include_directories" for cmake commands but when listing source files we can also use the taget_sources() command.
That means if a CMakeLists.txt is the same folder as the source files it should work to write:
target_sources(tests parser.cpp)
inside the CMakeLists.txt file of the 'source' folder.
Maybe there are problems because the target is not know yet. I only used target_sources() in sub folders of the project containing the source. Whereby I use a structure similar to:
whereby the src and inc folder also contain a CMakeLists.txt file that explicit lists the source files using target_sources() command.
Upvotes: 2