CMake无法正确链接库求助(附作业项目结构)
Let’s work through your CMake issues step by step to get your shared library (src.so) and Google Test setup working properly. First, let’s recap your project structure clearly to make sure we’re on the same page:
. ├── CMakeLists.txt ├── main.c # Contains only "Hello, world" ├── src │ ├── CMakeLists.txt │ ├── game │ │ ├── game.c │ │ └── game.h │ └── main.c └── test ├── CMakeLists.txt ├── homework_tests │ ├── CMakeLists.txt │ ├── gtest.cpp │ └── gtest.h └── lib └── googletest └── googletest └── [library files (not compiled)]
Step 1: Root CMakeLists.txt Setup
First, we need to configure the root CMakeLists.txt to set up the project, enable C/C++ support, and point CMake to your source and test directories:
cmake_minimum_required(VERSION 3.10) project(HomeworkProject C CXX) # Enforce standard versions for compatibility set(CMAKE_C_STANDARD 99) set(CMAKE_CXX_STANDARD 11) # Add subdirectories to build source and test targets add_subdirectory(src) add_subdirectory(test) # Optional: Build the top-level "Hello World" main.c as a separate executable add_executable(top_level_main main.c)
This ensures CMake knows about all your code paths and sets consistent standards for compilation.
Step 2: Build src.so from the src Directory
Your goal here is to create a shared library from the game module (we’ll exclude src/main.c since libraries don’t need a main function). Update src/CMakeLists.txt like this:
# Collect all source files from the game subdirectory file(GLOB GAME_SOURCES game/*.c) # Build the shared library (will output as src.so) add_library(src SHARED ${GAME_SOURCES}) # Make game.h accessible to other targets (like tests) target_include_directories(src PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/game) # Optional: If you want to build src/main.c as an executable linked to src.so add_executable(src_main main.c) target_link_libraries(src_main PRIVATE src)
The PUBLIC flag ensures any target linking against src.so automatically gets access to the game header directory.
Step 3: Configure Google Test in the test Directory
Since your Google Test files are uncompiled, we need to tell CMake to build the library from source. Update test/CMakeLists.txt:
# Add the Google Test source directory so CMake compiles it add_subdirectory(lib/googletest/googletest) # Include Google Test headers so your test files can find gtest/gtest.h include_directories(${gtest_SOURCE_DIR}/include ${gtest_SOURCE_DIR}) # Point CMake to your test implementation directory add_subdirectory(homework_tests)
Step 4: Link Tests to src.so & Google Test
Finally, update test/homework_tests/CMakeLists.txt to compile your tests and link them to both your shared library and Google Test:
# Collect your test source files file(GLOB TEST_SOURCES *.cpp) # Build the test executable add_executable(homework_tests ${TEST_SOURCES}) # Link against your shared library and Google Test libraries target_link_libraries(homework_tests PRIVATE src gtest gtest_main) # Enable test discovery so you can run tests with `ctest` enable_testing() add_test(NAME HomeworkTests COMMAND homework_tests)
Key Fixes Explained
- Shared Library Cleanup: We excluded
src/main.cfrom the library since libraries shouldn’t contain a main function—this avoids unnecessary code and potential conflicts. - Google Test Compilation: Using
add_subdirectoryon the Google Test source ensures CMake builds the library for your specific system, eliminating linking mismatches. - Header Visibility: Using
target_include_directories(forsrc.so) andinclude_directories(for Google Test) ensures all targets can find the headers they need without hardcoding paths. - Proper Linking Order: Listing your shared library first in
target_link_librariesensures CMake resolves dependencies correctly when linking the test executable.
Verify the Setup
To test everything works:
- Create a build directory and navigate into it:
mkdir build && cd build - Generate build files with CMake:
cmake .. - Build all targets:
make -j$(nproc) - Run your tests:
ctest
You should see src.so in the build/src directory, and your tests should run successfully if your test implementation is correct.
内容的提问来源于stack exchange,提问作者Dennis Barzanoff

