Specifying Include Directories
In real projects, header files are usually stored in a separate include/ directory. To allow the compiler to locate these headers, CMake must be told where to look. This is done using the target_include_directories command, which attaches include paths directly to a specific target.
CMakeLists.txt
12345678cmake_minimum_required(VERSION 3.10) project(SampleIncludeProject) add_library(mylib src/mylib.c) target_include_directories(mylib PUBLIC include) add_executable(main src/main.c) target_link_libraries(main PRIVATE mylib)
In this example, target_include_directories(mylib PUBLIC include) tells CMake to add the include/ directory to the compilerβs search path for the mylib library. Because PUBLIC is used, any executable that links to mylib also receives this include path automatically.
Include directories should be assigned to specific targets instead of being applied globally. This keeps your build configuration clean and avoids accidental dependencies.
Controlling Header Visibility
CMake allows you to control who can see which headers. This helps maintain clear boundaries between public APIs and internal implementation details.
CMakeLists.txt
123456789101112cmake_minimum_required(VERSION 3.10) project(IncludeVisibilityExample) add_library(core src/core.c) target_include_directories(core PUBLIC include/core PRIVATE src/private_headers INTERFACE include/interfaces ) add_executable(main src/main.c) target_link_libraries(main PRIVATE core)
Here, include/core is visible to both the core library and any program that links to it. The src/private_headers directory is used only inside the library and is hidden from other targets. The include/interfaces directory is not used by the library itself but becomes visible to anything that links against it.
This setup enforces encapsulation and prevents consumers of the library from relying on internal headers.
Thanks for your feedback!
Ask AI
Ask AI
Ask anything or try one of the suggested questions to begin our chat
Can you explain the difference between PUBLIC, PRIVATE, and INTERFACE in more detail?
How do I decide which keyword to use for my headers?
Can you give an example of how to structure my CMakeLists.txt for a library with both public and private headers?
Awesome!
Completion rate improved to 6.67
Specifying Include Directories
Swipe to show menu
In real projects, header files are usually stored in a separate include/ directory. To allow the compiler to locate these headers, CMake must be told where to look. This is done using the target_include_directories command, which attaches include paths directly to a specific target.
CMakeLists.txt
12345678cmake_minimum_required(VERSION 3.10) project(SampleIncludeProject) add_library(mylib src/mylib.c) target_include_directories(mylib PUBLIC include) add_executable(main src/main.c) target_link_libraries(main PRIVATE mylib)
In this example, target_include_directories(mylib PUBLIC include) tells CMake to add the include/ directory to the compilerβs search path for the mylib library. Because PUBLIC is used, any executable that links to mylib also receives this include path automatically.
Include directories should be assigned to specific targets instead of being applied globally. This keeps your build configuration clean and avoids accidental dependencies.
Controlling Header Visibility
CMake allows you to control who can see which headers. This helps maintain clear boundaries between public APIs and internal implementation details.
CMakeLists.txt
123456789101112cmake_minimum_required(VERSION 3.10) project(IncludeVisibilityExample) add_library(core src/core.c) target_include_directories(core PUBLIC include/core PRIVATE src/private_headers INTERFACE include/interfaces ) add_executable(main src/main.c) target_link_libraries(main PRIVATE core)
Here, include/core is visible to both the core library and any program that links to it. The src/private_headers directory is used only inside the library and is hidden from other targets. The include/interfaces directory is not used by the library itself but becomes visible to anything that links against it.
This setup enforces encapsulation and prevents consumers of the library from relying on internal headers.
Thanks for your feedback!