0 makefile
在讲cmake参数之前,先回顾下makefile中的几个关键参数
用makefile编译程序时,会用到“-I”(大写i),“-L”(大写l),“-l”(小写l)等参数,
“-I”(大写i):表示包含头文件;
“-L”(大写l):表示库文件目录;
“-l”(小写l):表示链接库文件(包括动态库文件,静态库文件);
示例如下:
gcc -o hello hello.c -I /home/hello/include -L /home/hello/lib -lworld -I /home/hello/include表示将/home/hello/include目录作为第一个寻找头文件的目录,寻找的顺序是:/home/hello/include-->/usr/include-->/usr/local/include -L /home/hello/lib表示将/home/hello/lib目录作为第一个寻找库文件的目录,寻找的顺序是:/home/hello/lib-->/lib-->/usr/lib-->/usr/local/lib -lworld表示在上面的lib的路径中寻找libworld.so动态库文件(如果gcc编译选项中加入了“-static”表示寻找libworld.a静态库文件)
1. aux_source_directory
1> 语法:
aux_source_directory(< dir > < variable >)
2> 作用:
查找在某个路径下的所有源文件,搜集所有在指定路径下的源文件的文件名,将输出结果列表储存在dir变量中
3> 用法示例:
aux_source_directory(. DIR_SRCS)
查找当前目录下的所有源文件,并将名称保存到 DIR_SRCS 变量
2. add_executable
1> 语法:
add_executable (<name> [WIN32] [MACOSX_BUNDLE] [EXCLUDE_FROM_ALL] [source1] [source2 ...]) add_executable (<name> IMPORTED [GLOBAL]) add_executable (<name> ALIAS <target>)
2> 作用:
使用给定的源文件,为工程引入一个可执行文件,并且在工程范围内必须是全局唯一的
3> 用法示例:
ADD_EXECUTABLE(hello ${SRC_LIST})
定义了这个工程会生成一个文件名为hello的可执行文件,相关的源文件是SRC_LIST中定义的源文件列表
3. add_subdirectory
4. add_library
1> 语法:
add_library(<name> [STATIC | SHARED | MODULE] [EXCLUDE_FROM_ALL] [source1] [source2 ...])
2> 作用:
添加名为name的库,库的源文件可指定,也可用target_sources()后续指定。
库的类型是STATIC(静态库)/SHARED(动态库)/MODULE(模块库)之一。
name属性必须全局唯一
生成的library名会根据STATIC或SHARED成为name.a或name.so
这里的STATIC和SHARED可不设置,通过全局的BUILD_SHARED_LIBS的FALSE或TRUE来指定
3> 用法示例:
add_library (message SHARED message.cpp message.h )
指定生成的库为message,类型为shared动态库,需要的源文件是message.h和message.cpp
5. link_directories [makefile中-L]
1> 语法:
link_directories(directory1 directory2 ...)
2> 作用:
给出链接库的路径,让编译器可以找到链接符号
3> 用法示例:
LINK_DIRECTORIES(/home/myproject/libs)
就像Makefile使用-L来指定第三方库所在路径。cmake可以使用 LINK_DIRECTORIES 命令来指定第三方库所在路径,比如,你的动态库在/home/myproject/libs 这个路径下,则通过上面命令把该路径添加到第三方库搜索路径中,这样就可以使用相对路径了,使用TARGET_LINK_LIBRARIES的时候,只需要给出动态链接库的名字就行了,比如:
TARGET_LINK_LIBRARIES(MyApp -lcurl )
4> note:
cmake官方文档指出,link_directories不是必须,可以用find_package 和 find_library替代
6. link_libraries
cmake官方明确给出deprecate的标签,不用care
7. target_link_libraries [makefile中-l (小写的L)]
1> 语法:
target_link_libraries(<target> [item1 [item2 [...]]] [[debug|optimized|general] <item>] ...)
2> 作用:
指定生成target所需要依赖的库文件,相当于Makefile中的 -l参数
3> 用法示例:
target_link_libraries (hello protobuf jsoncpp)
指定生成的目标为hello, 所依赖的库有protobuf和jsoncpp
8. include_directories [makefile中的-I (大写的i)]
1> 语法:
include_directories ([AFTER|BEFORE] [SYSTEM] dir1 [dir2 ...])
2> 作用:
将指定目录添加到编译器的头文件搜索路径之下,指定的目录被解释成当前源码路径的相对路径。
3> 用法示例:
include_directories (${SRC}/include
将src/include目录添加到头文件目录搜下路径
总结一下
使用三方库需要用到的关键字:
link_directories 指定库的路径 include_directories 指定头文件路径 target_link_libraries 链接库(不需要再指定路径)
target_link_libraries应该放在add_executable之前
Tips:
1> 通过cmake指定安装路径,使用参数
cmake -DCMAKE_INSTALL_PREFIX=/usr ..
9. exec_program
deprecated,用exec_process代替