簡體   English   中英

HelloWorld:使用CMake下載,構建和鏈接Boost

[英]HelloWorld: downloading, building and linking Boost using CMake

我有一個Hello,World風格的程序,我希望使用CMake以端到端的方式進行更多工作。 在這種情況下,這意味着我可以下載Boost庫,編譯它們,最后編譯我的小Hello,World並將Boost庫鏈接到它。

目錄布局目前看起來像這樣

cmaketest
|- build //I would like to have here the CMake generated IDE files.
|- src
   |- main.cpp
   |- hello.cpp
   |- hello.hpp
|- depends //I would like to have here the built Boost libraries and headers.
|- downloads //This contains the downloaded zip file.
|- temp //Temporary files.

我有以下CMakeLists.txt ,目前我生成Visual Studio 2015項目文件,如下所示: cmake build -G "Visual Studio 14 2015 Win64" 一切都很好,我會開始解決方案, CMake抱怨它無法找到Boost,去下載它開始構建(在下面的代碼我設置為獲取以前獲取的文件)。 但是經過一段時間的建設,問題就出現了......

  1. Boost文件似乎出現在\\cmaketest\\CMakeFiles\\build\\Boost-prefix\\src\\Boost作為根。 我怎么能這些它們被構建為\\depends\\boost (或者那個效果)以及如何包含要鏈接到解決方案的庫? 這個鏈接是一個單獨的問題,我知道如何包含這個奇怪目錄中的標題,但它並不是我想要的。
  2. 看起來VS IDE首先警告不要找到Boost頭文件(不久見主程序),然后啟動Boost構建。 這可以避免嗎?
  3. 如何讓Boost庫從VS解決方案中消失? 即不是要創建它的項目,而只是依賴於頭文件和庫?
  4. 是否有內置方法可以避免下載Boost軟件包(如果已經在磁盤上)? 看起來它將在任何情況下被檢索,我已經考慮過檢查文件是否存在。

main.cpp (我想這是這種情況下的相關文件)

//The Boost headers are included just to check the linker.
#include "hello.hpp"
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/date_time/posix_time/posix_time_io.hpp>
#include <iostream>
using std::cout;
using std::endl;

int main()
{
    hello helloer;
    cout << helloer.greet("World here") << endl;

    return EXIT_SUCCESS;
}

然后是CMakeLists.txt文件。

cmake_minimum_required(VERSION 3.6 FATAL_ERROR)
set(CMAKE_VERBOSE_MAKEFILE ON)
project(Cmaketest)

if(POLICY CMP0042)
   cmake_policy(SET CMP0042 NEW)
endif()

if(POLICY CMP0066)
   cmake_policy(SET CMP0066 NEW)
endif()

# Default build type if none was specified.
if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
  set(CMAKE_BUILD_TYPE Debug CACHE STRING "Choose the type of build." FORCE)
  message(STATUS "Setting build type to '${CMAKE_BUILD_TYPE} as none was specified.")

  # Possible values of build type for CMake GUI.
  set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS "Debug" "Release" "MinSizeRel" "RelWithDebInfo")
endif()

# The path to extra modules.
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/cmake)

# Setup build locations.
if(NOT CMAKE_RUNTIME_OUTPUT_DIRECTORY)
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin)
endif()
set(CMAKE_CURRENT_BINARY_DIR    
${CMAKE_CURRENT_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/build)

set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)

include(ExternalProject)
include(ProcessorCount)
ProcessorCount(N)
if(NOT N EQUAL 0)
    set(CMAKE_BUILD_FLAGS -j${N})
endif()
# set(BOOST_VERSION 1.63.0)
# Boost related settings:    
# https://cmake.org/cmake/help/v3.6/module/FindBoost.html.
# Should one check the environment variables and flags here explicitly
# to remove the complaint about missing Boost library? Or should perhaps
# BOOST_ROOT be set? Point to what?
find_package(Boost)
if(NOT Boost_FOUND)
    # It shouldn't hurt to enable extensive diagnostics, just in case.
    # Also, a different set of files is downloaded for UNIX and WIN32
    # due to file permissions and line-feeds (Windows should handle
    # also Unix style line-feeds).
    set(Boost_DETAILED_FAILURE_MSG on)
    add_definitions(${Boost_LIB_DIAGNOSTIC_DEFINITIONS})
    set(Boost_Bootstrap_Command)
    if(UNIX)
       set(Boost_Url     "http://sourceforge.net/projects/boost/files/boost/1.63.0/boost_1_63_0.tar.gz")
        set(Boost_Sha1 "2cecf1848a813de55e5770f324f084c568abca0a")
        set(Boost_Bootstrap_Command ./bootstrap.sh)
        set(Boost_b2_Command ./b2)
     elseif(WIN32)
        set(Boost_Url "http://sourceforge.net/projects/boost/files/boost/1.63.0/boost_1_63_0.zip")
        set(Boost_Sha1 "4364989afbe6b11f2d5e59df902c3ca4d7851824")
        set(Boost_Bootstrap_Command bootstrap.bat)
        set(Boost_b2_Command b2.exe)
    endif()
        set(Config_Libraries "chrono,filesystem,program_options,system,thread,test")
ExternalProject_Add(Boost
    TMP_DIR "${CMAKE_CURRENT_SOURCE_DIR}/temp"
    DOWNLOAD_DIR "${CMAKE_CURRENT_SOURCE_DIR}/downloads"
    URL "${CMAKE_CURRENT_SOURCE_DIR}/downloads/boost_1_63_0.zip"
    URL_HASH "SHA1=${Boost_Sha1}"
    BUILD_IN_SOURCE 1
    UPDATE_COMMAND ""
    PATCH_COMMAND ""
    CONFIGURE_COMMAND ${Boost_Bootstrap_Command} --without-icu --with_libraries=${Config_Libraries}
    BUILD_COMMAND  ${Boost_b2_Command}
        # --prefix="${CMAKE_CURRENT_SOURCE_DIR}/depends"
        --without-python
        --address-model=64
        --architecture=x64
        --threading=multi
        --link=static
        --variant=release
        --layout=tagged
        --build-type=complete
        -j${N}
    INSTALL_COMMAND ""
    # INSTALL_DIR "${CMAKE_CURRENT_SOURCE_DIR}/depends"

    #As it happens, these directories are currently empty...
    # set(BOOST_ROOT ${CMAKE_CURRENT_SOURCE_DIR}/depends/include/boost-1_63)
    # set(Boost_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/depends/boost_1_63/include)
    # set(Boost_LIBRARY ${CMAKE_CURRENT_SOURCE_DIR}/depends/boost_1_63/lib)
)
endif()

 set(Boost_USE_STATIC_LIBS OFF)
 set(Boost_USE_MULTITHREADED ON)
 set(Boost_USE_STATIC_RUNTIME OFF)
 include_directories(${CMAKE_SOURCE_DIR}/src)

# Grabbing just all the test project files.
file(GLOB SOURCES "src/*.*")
add_executable(cmaketest ${SOURCES})
# TARGET_LINK_LIBRARIES(cmaketest ${Boost_LIBRARY})

我會嘗試給你一些提示,試着回答你的問題。

1)使用此代碼段,您應該能夠在正確的目錄中擁有源和構建的文件。 我保留了TMP_DIR "${Cmaketest_SOURCE_DIR}/temp"但在我的項目中我不使用該行。

ExternalProject_Add(Boost
    TMP_DIR "${Cmaketest_SOURCE_DIR}/temp"
    DOWNLOAD_DIR "${Cmaketest_SOURCE_DIR}/downloads"
    URL "${Cmaketest_SOURCE_DIR}/downloads/boost_1_63_0.zip"
    URL_HASH "SHA1=${Boost_Sha1}"
    SOURCE_DIR ${Cmaketest_SOURCE_DIR}/downloads/boost_1_63_0
    BUILD_IN_SOURCE 1
    UPDATE_COMMAND ""
    PATCH_COMMAND ""
    CONFIGURE_COMMAND ${Boost_Bootstrap_Command} --without-icu --with_libraries=${Config_Libraries}
    BUILD_COMMAND  ${Boost_b2_Command}
        --prefix="${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0"
        --without-python
        --address-model=64
        --architecture=x64
        --threading=multi
        --link=static
        --variant=release
        --layout=tagged
        --build-type=complete
        -j${N}
    INSTALL_COMMAND ${Boost_b2_Command} --prefix="${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0" --without-python
        --address-model=64
        --architecture=x64
        --threading=multi
        --link=static
        --variant=release
        --layout=tagged
        --build-type=complete
        -j${N} install
    INSTALL_DIR "${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0"
)

set(BOOST_ROOT ${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0)
set(Boost_LIBRARY ${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0/lib)
set(Boost_INCLUDE_DIR ${Cmaketest_SOURCE_DIR}/depends/boost_1_63_0/include)
include_directories(${Boost_INCLUDE_DIR})

要注意到你沒有調用“install”,所以一旦在“奇怪”目錄中構建,文件就不會移動到指定的前綴。 另請注意使用${Cmaketest_SOURCE_DIR}而不是之前的。
嘗試打印兩者,看看是否有區別。

2)為了解決在沒有找到Boost的情況下你會得到的警告,你應該寫:

find_package(Boost QUIET)  

3)為了解決這個問題,我猜你無法生成項目文件,而不是生成項目文件

cmake build -G "Visual Studio 14 2015 Win64"  

只是有cmake . 或者cmake ..取決於你是否會進行源內或源外構建。 我建議做一些源外構建,但這是你的選擇。
4) FindBoost.cmakeFindBoost.cmake )使您可以將任意路徑傳遞到Boost目錄。 您可以在配置中使用它來提示CMake在您給出的位置查找Boost,例如,您將通過以下方式調用cmake:

cmake -DBOOST_ROOT=/path_to_cmaketest_dir/depends/boost_1_63_0 ..  

如果您的系統可能挑剔,您可以指定所有內容:

cmake -DBOOST_ROOT=/path_to_cmaketest_dir/depends/boost_1_63_0 -DBOOST_LIBRARYDIR=/path_to_cmaketest_dir/depends/boost_1_63_0/lib DBOOST_INCLUDEDIR=/path_to_cmaketest_dir/depends/boost_1_63_0/include ..  

請注意,在最后兩個片段中,我假設了一個源外構建的配置。
另請注意,如果您已安裝或已下載Boost軟件包,則在1)中的${Cmaketest_SOURCE_DIR}代碼中使用${Cmaketest_SOURCE_DIR}也應該解決4)所以當它找不到Boost時它會嘗試下載但是它不會,因為現在cmake應該能夠看到文件(.zip)。

請參閱CMaker_Boost ,在配置時使用CMake構建Boost。 現在它在Linux和Android,gcc和clang上進行了測試。 其他系統未經過測試。 我希望這有幫助。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM