使用CMake构建复杂工程

0. 什么是CMake

  CMake是一个跨平台的编译、安装、测试以及打包工具;CMake不直接编译软件,而是结合原生构建系统来构建软件。CMake配置文件是CMakeList.txt文件(每个源码文件夹下都要有一个),CMake根据配置文件在生成Unix的Makefile或VS的solution文件等。

1. 为什么选CMake

  别人为什么选CMake我不清楚,我是因为在Linux上直接写Makefile太痛苦,而项目又会跨平台,Windows和Linux都要有

2. 用一个简单工程来说明CMake用法。

  • 工程名soTest,里面包含一个两个so(dll)文件:so1和so2,以及一个测试工程st
  • 工程内文件结构如下:
    • 文件so1/so1.c:用于生成libso1.so
    • 文件so2/so2.c:用于生成libso2.so,依赖于libso1.so,会调用libso1.so内函数
    • 文件test/test.c:生成可执行文件,调用libso2.so,调用libso2.so内函数
    • 文件test/test.py:使用python调用libso2.so函数
    • build目录用于存放编译时和种文件,这样可以保持源代码文件夹干净
    • 文件结构
    • 可以看,每个目录下都有一个CMakeList.txt的文件,这些文件就是CMake的配置文件,CMake就是根据这些文件来生成其他构建文件的

3. 项目代码如下:

  

1 // so1/so1.c
2 int add_fun(int a, int b)
3 {
4     return a+b;
5 }
1 // so1.h
2 #ifndef _so1_h_
3 #define _so1_h_
4
5 int add_fun(int a, int b);
6 int fun_test(int a);
7
8 #endif//_so1_h_
 1 // so2/so2.h
 2 #include <stdio.h>
 3 #include <stdlib.h>
 4 #include "so1.h"
 5
 6 int fun_test(int a)
 7 {
 8     for (int i=0; i<a; ++i)
 9     {
10         printf("add_fun(%d+%d)=%d\n", i, i, add_fun(i, i));
11     }
12
13     return 0;
14 }
 1 // test/test.c
 2 #include <stdio.h>
 3 #include <stdlib.h>
 4
 5 #include "so1.h"
 6
 7 int main(int argc, char **argv)
 8 {
 9     return fun_test(9);
10 }
 1 # ./CMakeLists.txt,工程总配置文件
 2
 3 # 最低版本要求,必须
 4 cmake_minimum_required(VERSION 3.0)
 5
 6 # 工程名称,这里用soTest这个名字
 7 project(soTest)
 8
 9 # 添加include目录,本例中关文件在./下,所以直接取${PROJECT_SOURCE_DIR}/
10 include_directories(${PROJECT_SOURCE_DIR}/)
11
12 # 添加链接库查找目录,库查找序按照参数顺序从向右查
13 link_directories(${PROJECT_BINARY_DIR}/libs /usr.local/libs /usr/lib)
14
15 # 设置生成的库文件目录,这里我们设置成和库目录相同
16 set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/libs)
17
18 # 设置可执行文件目录,同样设成和库目录相同
19 set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}/libs)
20
21 # 添加子目录(每个子目录下都必须有自已的CMakeLists.txt文件
22 add_subdirectory(so1)
23 add_subdirectory(so2)
24 add_subdirectory(test)
# ./so1/CMakeLists.txt
# project name: soTest
project(soTest)

# set source files
set(so1 so1.c)

# set make to a shared library
add_library(so1 SHARED ${so1})
 1 # ./so2/CMakeLists.txt
 2
 3 project(soTest)
 4 set(so2 so2.c)
 5 add_library(so2 SHARED ${so2})
 6
 7 # link so1
 8 target_link_libraries(so2 so1)
1 project(soTest)
2 set(st test.c)
3
4 # 生成可执行文件
5 add_executable(st test.c)
6 target_link_libraries(st so2 so1)

4. CMake支持在源文件目录外进行构建,这里我们选择在./build目录下进行构建,好处是不会把源文件目录污染,在build目录下运行命令(命令后参数是总CMakeLists.txt文件所在目录):

cmake .. && make && ./libs/st

  命令运行后结果如下

  

时间: 2024-10-29 19:12:39

使用CMake构建复杂工程的相关文章

学习使用CMake构建工程

本文记录学习使用CMake的过程. 安装CMake请参考: http://blog.csdn.net/alex_my/article/details/17310001 本文使用Win7X64, VS2012. 参考了这篇文章: http://blog.csdn.net/fan_hai_ping/article/details/8208898 本文所用到的代码已打包: http://download.csdn.net/detail/alex_my/6904069 请耐心一行行的看下去! 目录: 1

CMake命令:CMake构建系统的骨架

CMake命令:CMake构建系统的骨架 80个命令(转载自http://www.cnblogs.com/coderfenghc/archive/2012/06/16/CMake_ch_01.html#2996205) CMD#1: add_custom_command为生成的构建系统添加一条自定义的构建规则. add_custom_command命令有两种主要的功能:第一种是为了生成输出文件,添加一条自定义命令. add_custom_command(OUTPUT output1 [outpu

CMake构建NDK项目提示asm/types.h找不到

用CMake构建NDK项目时,会传入toolchain的cmake脚本文件android.toolchain.cmake给CMake.这个文件中会做若干设定,其中就包括include路径. 我遇到的情况是,自己手动修改CMAKE_C_FLAGS和CMAKE_CXX_FLAGS时,覆盖了它们原有的(android.toolchain.cmake修改后的)值,导致asm/types.h找不到. 我的错误设定: set(CMAKE_C_FLAGS "${MY_CMAKE_C_FLAGS}")

eclipse+maven+tomcat构建web工程

我们要利用Maven构建一个web应用,开发环境为eclipse+tomcat.构建过程如下: 1.工具准备 eclipse:版本为eclipse 4.2(Juno Service),maven插件的安装与配置参见"m2eclipse安装与配置" tomcat:版本为apache-tomcat-6.0.37(即tomcat6.x系列,本文安装在D:\work\tomcat6\apache-tomcat-6.0.37-maven) 2.建立web应用 我们使用eclipse建立maven

CMAKE设置VS工程中Debug和Release不同的输出名称

CMAKE在管理工程时,需要同时编译Debug和Release版本,但是两个版本输出的文件无论是lib还是dll,名称都是是完全相同. 如果要输出在同一个目录中是非常麻烦的,非常容易混淆,可以使用以下命令设置debug和Release输出文件后缀的方式进行区分: if(WIN32 AND NOT MINGW) if(NOT DEFINED CMAKE_DEBUG_POSTFIX) set(CMAKE_DEBUG_POSTFIX "_debug") endif() if(NOT DEFI

使用BLADE构建c++工程管理

使用BLADE构建c++工程管理 字数764 阅读2753 评论2 喜欢4 一. c++工程依赖管理 之前在百度一直使用comake2构建c++项目,十分方便.免去了手写Makefile的痛苦,很多项目都不需要从零开始,其中的一个配置类似如下: WORKROOT('../../../')CopyUsingHardLink(True)CPPFLAGS('-D_GNU_SOURCE -D__STDC_LIMIT_MACROS -DVERSION=\\"1.9.8.7\\"')CFLAGS(

通过rebar构建erlang工程

1.创建一个项目文件夹: mkdir myapp cd myapp 2.下载rebar的二进制文件到这个项目的文件夹. git clone https://github.com/basho/rebar.git; 3.使用rebar模板系统构建我们工程的“骨架”. rebar creat-app appid=myapp 这条命令执行后会在项目文件中产生一个子文件夹“src”,其包含三个文件: myapp.app.src:otp应用程序的资源文件 myapp_app.erl:一个OTP应用程序的Ap

linux下cmake编译C++工程之总结篇

昨天正式把项目编译完成,经历了一周的摸索和折磨后,最后也想:oh,it's so easy! 但是过程确实困难的,因为cmake官方只有API的解释,而且解释的不是很清楚. 一般项目都是狠复杂的层级关系 这种如何来写cmake呢? 首先要知道一个很重要的东西,cmake是一定要从顶级目录开始,才能继承目录,比如直接在project1目录里用../lib是无效的,因为cmake并不知道: 而如果在project下建立cmakelists.txt 然后add_subdir(project1),pro

使用Gradle构建Android工程

Gradle是以Groovy语言为基础,基于DSL语法的构建工具,它通过插件的方式定制工程构建过程.Google开发了Android Gradle插件,使用Gradle构建Android工程. Gradle构建Android工程,我们可以在Android studio中使用,也可以在命令行中使用,也可以集成到持久化集成工具中. Gradle构建Android工程的配置文件名是build.gradle,存放在工程的根目录下. 一个Android工程(Project)是由一个或多个组件(Module