--- title: CMake学习笔记 date: 2017-12-27 13:54:05 tags: [cmake, visual studio] categories: cmake --- 本文主要记录CMake学习过程的一些笔记。 ## 基本文件结构 编写CMakeLists.txt ``` # CMake 最低版本号要求 cmake_minimum_required (VERSION 2.8) # 项目信息 project (Demo1) # 指定生成目标 add_executable(Demo main.cc) ``` ## 常用命令 ### 项目类型命令 - `add_executable`可执行文件 - `add_library` 静态库 ### 文件依赖命令 - `aux_source_directory( )` 查找指定目录下的所有源文件,然后将结果保存进指定的变量名。 ``` # CMake 最低版本号要求 cmake_minimum_required (VERSION 2.8) # 项目信息 project (Demo2) # 查找当前目录下的所有源文件 # 并将名称保存到 DIR_SRCS 变量 aux_source_directory(. DIR_SRCS) # 指定生成目标 add_executable(Demo ${DIR_SRCS}) ``` 这样,CMake 会将当前目录所有源文件的文件名赋值给变量`DIR_SRCS`,再指示变量`DIR_SRCS` 中的源文件需要编译成一个名称为 Demo 的可执行文件。 - `add_subdirectory(source_dir [binary_dir] [EXCLUDE_FROM_ALL])` 添加子文件夹到构建系统中。 `source_dir`子文件夹路径 `binary_dir` 输出路径 `EXCLUDE_FROM_ALL` 从Build All项目中排除 ### 编译选项命令 - Visual Studio to CMake Mapping ![VS-to-CMake-Mapping](VS-to-CMake-Mapping.png) ![CMake-Projects](CMake-Projects.png) > ZERO_CHECK will rerun cmake. You can/should execute this after changing something on your CMake files. > ALL_BUILD is simply a target which builds all and everything project in the active solution, I guess one can compare it to "make all". > 可以通过`set(CMAKE_SUPPRESS_REGENERATION true)`不生成`ZERO_CHECK`工程。 ### 链接命令 - `target_link_libraries`指明链接库 `target_link_libraries( [lib1 [lib2 [...]]] [[debug|optimized|general] ] ...)` `general`可选字段,表示所有模式都链接的库 `debug`表示debug模式才链接的库 `optimized`表示非debug模式才链接的库 ```cmake target_link_libraries(${PROJECT_NAME} delayimp.lib libcef.lib debug cef_module_d.lib debug libcef_dll_wrapper_d.lib optimized cef_module.lib optimized libcef_dll_wrapper.lib) ``` ## 项目实例 ### 自定义编译选项 顶层CMakeLists.txt文件 ``` # CMake 最低版本号要求 cmake_minimum_required (VERSION 2.8) # 项目信息 project (Demo4) # 加入一个配置头文件,用于处理 CMake 对源码的设置 configure_file ( "${PROJECT_SOURCE_DIR}/config.h.in" "${PROJECT_BINARY_DIR}/config.h" ) # 是否使用自己的 MathFunctions 库 option (USE_MYMATH "Use provided math implementation" ON) # 是否加入 MathFunctions 库 if (USE_MYMATH) include_directories ("${PROJECT_SOURCE_DIR}/math") add_subdirectory (math) set (EXTRA_LIBS ${EXTRA_LIBS} MathFunctions) endif (USE_MYMATH) # 查找当前目录下的所有源文件 # 并将名称保存到 DIR_SRCS 变量 aux_source_directory(. DIR_SRCS) # 指定生成目标 add_executable(Demo ${DIR_SRCS}) target_link_libraries (Demo ${EXTRA_LIBS}) ``` 编写`config.h.in`文件 `#cmakedefine USE_MYMATH` ### 设置编译模式 ``` set(CMAKE_BUILD_TYPE "Debug") set(CMAKE_CXX_FLAGS_DEBUG "$ENV{CXXFLAGS} -O0 -Wall -g -ggdb") set(CMAKE_CXX_FLAGS_RELEASE "$ENV{CXXFLAGS} -O3 -Wall") ``` ### 环境检查 首先在顶层 CMakeLists 文件中添加 CheckFunctionExists.cmake 宏,并调用 `check_function_exists` 命令测试链接器是否能够在链接阶段找到 pow 函数。 ``` # 检查系统是否支持 pow 函数 include (${CMAKE_ROOT}/Modules/CheckFunctionExists.cmake) check_function_exists (pow HAVE_POW) ``` ### 设置libcurl运行时环境 ```cmake if(USE_ALLMT_) target_compile_definitions(libcurl PRIVATE -DRTLIBCFG=static) set_property(TARGET libcurl APPEND_STRING PROPERTY COMPILE_OPTIONS $,/MTd,/MT>) else() target_compile_definitions(libcurl PRIVATE -DRTLIBCFG=shared) set_property(TARGET libcurl APPEND_STRING PROPERTY COMPILE_OPTIONS $,/MDd,/MD>) endif() ``` ## 参考链接 - [cmake-and-visual-studio](https://cognitivewaves.wordpress.com/cmake-and-visual-studio/) - [CMake手册](https://www.zybuluo.com/khan-lau/note/254724) - [CMakeLists.txt](http://wiki.ros.org/catkin/CMakeLists.txt)