cmake find_package的基本原理与详细示例(二):find_package的Module模式简单示例——查找自定义模块

简单的find_package Module模式示例,通过Findxxx.cmake查找依赖库的安装信息。

一、目录结构如下:

                                      

二、代码文件&安装目录:

1、lib目录:

demo.h:

#include <iostream>
#include <string>

namespace test{

    std::string run();

}

demo.cpp:

#include "demo.h"

namespace test{

    std::string run()
    {
        return "find_package_demo";
    }
}

CMakeLists.txt:

cmake_minimum_required( VERSION 3.8 FATAL_ERROR)
project(demo VERSION 1.0.0 LANGUAGES CXX)
SET(CMAKE_EXPORT_COMPILE_COMMANDS ON)

set(PROJECT_ROOT ${CMAKE_CURRENT_LIST_DIR}/..)
set(CMAKE_INSTALL_PREFIX ${PROJECT_ROOT}/install/)#安装目录

#set compile flags
#add_definitions(-std=c++11 -g -rdynamic)
set(CMAKE_CXX_FLAGS "-g3 -rdynamic -std=c++11")
set(CMAKE_CXX_FLAGS_DEBUG "-O0 -fsanitize=address -fno-omit-frame-pointer -fsanitize=leak")
set(CMAKE_CXX_FLAGS_RELEASE "-O3 -DNDEBUG")


SET(BIN_DESTINATION ${PROJECT_SOURCE_DIR}/bin)
SET(INSTALL_DESTION ${PROJECT_SOURCE_DIR}/install)
SET(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${BIN_DESTINATION})
SET(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${BIN_DESTINATION})
SET(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${BIN_DESTINATION})

#include dirs
include_directories(./)

#libraries
SET(SRC demo.cpp)
add_library(demo SHARED ${SRC})
SET_TARGET_PROPERTIES(demo PROPERTIES VERSION ${PROJECT_VERSION}) 
SET_TARGET_PROPERTIES(demo PROPERTIES PUBLIC_HEADER ${CMAKE_CURRENT_LIST_DIR}/demo.h)

install(TARGETS demo
    EXPORT  demo
    LIBRARY DESTINATION lib  # 动态库安装路径
    ARCHIVE DESTINATION lib  # 静态库安装路径
    RUNTIME DESTINATION bin  # 可执行文件安装路径
    PUBLIC_HEADER DESTINATION include  # 头文件安装路径
    )

2、main目录

main.cpp:

#include <iostream>
#include <string>

#include "demo.h"

using namespace std;

int main(int argc,char *argv[])
{
    cout<<"main..."<<endl;
    cout<<test::run()<<endl;
    cout<<"exit."<<endl;
    return 0;
}

CMakeLists.txt:

cmake_minimum_required( VERSION 3.8 FATAL_ERROR)
project(main VERSION 1.0.0 LANGUAGES CXX)
SET(CMAKE_EXPORT_COMPILE_COMMANDS ON)

set(PROJECT_ROOT ${CMAKE_CURRENT_LIST_DIR}/..)
message(${PROJECT_ROOT})
set(CMAKE_INSTALL_PREFIX ${PROJECT_ROOT}/install/)

#set compile flags
#add_definitions(-std=c++11 -g -rdynamic)
set(CMAKE_CXX_FLAGS "-g3 -rdynamic -std=c++11")
set(CMAKE_CXX_FLAGS_DEBUG "-O0 -fsanitize=address -fno-omit-frame-pointer -fsanitize=leak")
set(CMAKE_CXX_FLAGS_RELEASE "-O3 -DNDEBUG")

#set dirs
SET(BIN_DESTINATION ${PROJECT_SOURCE_DIR}/bin)
SET(INSTALL_DESTION ${PROJECT_SOURCE_DIR}/install)
SET(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${BIN_DESTINATION})
SET(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${BIN_DESTINATION})
SET(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${BIN_DESTINATION})


#设置查找Finddemo.cmake的路径
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_LIST_DIR}/cmake/)
message("cmake_module_path:${CMAKE_MODULE_PATH}")

#使用find_package查找demo(这里会从CMAKE_MODULE_PATH设置的路径中查找)
find_package(demo REQUIRED MODULE)

#如果找到了(demo_FOUND会被设置为True,是一种约定,你也可以使用自己喜欢的变量<但是不建议这么做>)
if (demo_FOUND)
    #打印相关的信息
    message("demo_FOUND:${demo_FOUND}")
    message("demo_version:${demo_VERSION}")
    message("demo_include:${demo_INCLUDE_DIR}")
    message("demo_library:${demo_LIBRARY}")
endif()

#include dirs
include_directories(./ ${demo_INCLUDE_DIR}) #把demo.h所在的路径demo_INCLUDE_DIR添加到include dir中(Finddemo.cmake已经设置了demo_INCLUDE_DIR变量)
#link dirs
link_directories(${BIN_DESTINATION})

#execute 
SET(SRC_MAIN main.cpp)
add_executable( ${PROJECT_NAME} ${SRC_MAIN})
SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION}) 
target_link_libraries(${PROJECT_NAME} ${demo_LIBRARY}) #链接libdemo.so(Finddemo.cmake设置了demo_LIBRARY变量)

install(TARGETS main
    EXPORT  main
    LIBRARY DESTINATION lib  # 动态库安装路径
    ARCHIVE DESTINATION lib  # 静态库安装路径
    RUNTIME DESTINATION bin  # 可执行文件安装路径
    PUBLIC_HEADER DESTINATION include  # 头文件安装路径
    )

cmake目录:

Finddemo.cmake文件

message("now using Finddemo.cmake find demo lib")

#find demo.h
FIND_PATH(demo_INCLUDE_DIR demo.h 
    /usr/include/demo/ 
    /usr/local/demo/include/ 
    ~/work/demo/find_package_simple/install/include/)

message("include_dir: ${demo_INCLUDE_DIR}")

#find libdemo.so
FIND_LIBRARY(demo_LIBRARY libdemo.so 
    /usr/local/demo/lib/ 
    ~/work/demo/find_package_simple/install/lib/)

message("libs: ${demo_LIBRARY}")

if(demo_INCLUDE_DIR AND demo_LIBRARY)
    set(demo_FOUND TRUE)
    set(demo_VERSION 1.0.0)
endif(demo_INCLUDE_DIR AND demo_LIBRARY)

3、install目录

bin目录:

lib目录:

include目录:

三、find_package原理说明:

构建main的时候,cmake会在main目录的CMakeLists.txt的第24行指定的目录查找Finddemo.cmake文件,第28行的find_package(demo)通过Finddemo.cmake文件查找demo的安装信息(头文件、.so或.a、版本信息等等),Finddemo.cmake文件设置了与demo的安装信息相关的变量(demo_FOUND、demo_INCLUDE_DIR、demo_LIBRARY、demo_VERSION等),由demo_FOUND指示了是否查找成功,查找成功后即可在CMakeLists.txt文件中使用这些变量了

四、代码:

          详见https://download.csdn.net/download/lianshaohua/12830796

猜你喜欢

转载自blog.csdn.net/lianshaohua/article/details/108487599