在cmake中使用configure和make

/*******************************************************************
• 此文章解釋權歸windsome全部,如要轉載無須聯繫本人。
• 轉載須要包含此擡頭信息,若有疑問,歡迎聯繫本人。
• QQ: 35327864
• msn: fgwf1@hotmail.com
• mail: agooou@gmail.com
 ********************************************************************/linux

目前linux上各類工具軟件源碼包都是使用標準的gnu的configure進行打包。若是將這些開發包都使用cmake方式來改寫makefile系統,工做量將很巨大。比較好的方法是直接在cmake中進行configure而且make,而後使用生成的這些庫和頭文件。過程以下所述。c++

我是基於原先的一個項目上面加內容,項目路徑爲/home/Dev/DigitalSignage,項目名稱在CMakeList.txt中定義爲DS,其源碼根路徑爲DS_SOURCE_DIR=/home/Dev/DigitalSignage,其二進制目錄爲DS_BINARY_DIR=/home/Dev/DigitalSignage/build。個人cmake文件放在${DS_SOURCE_DIR}/cmake下。我新建了一個文件BuildGNUPackage.cmake用於咱們對標準gnu源碼庫進行操做。git

1,設置軟件包安裝路徑及編譯工具
SET(GNUPKG_INSTALL_PATH ${DS_BINARY_DIR}/gnupkg/install)
SE(GNUPKG_CC ${CMAKE_C_COMPILER})
SET(GNUPKG_CXX ${CMAKE_CXX_COMPILER})
IF(DS_ENABLE_CCACHE)
    SET(GNUPKG_CC ${CMAKE_C_COMPILER_ARG1})
    SET(GNUPKG_CXX ${CMAKE_CXX_COMPILER_ARG1})
ENDIF(DS_ENABLE_CCACHE)shell

2,編寫CONFIG_GNU_PACKAGE宏,用以對源碼包進行配置,_pkg_name爲軟件包名稱,如sigc++_config(後面帶_config的緣由是跟下面的BUILD_GNU_PACKAGE宏中名字區分開), _pkg_rpath爲相對於DS_SOURCE_DIR的相對路徑如3rdParties/libsigc++2.0,_pkg_options爲configure的參數,如--host=mips
MACRO(CONFIG_GNU_PACKAGE _pkg_name _pkg_rpath _pkg_options)
    SET(GNUPKG_SOURCE_PATH ${DS_SOURCE_DIR}/${_pkg_rpath})
    SET(GNUPKG_BINARY_PATH ${DS_BINARY_DIR}/gnupkg/${_pkg_rpath})
    SET(GNUPKG_CONFIG_TARGETS ${GNUPKG_CONFIG_TARGETS} ${_pkg_name})工具

    ADD_CUSTOM_TARGET(
        ${_pkg_name}
        COMMENT "config ing ${_pkg_name} in ${_pkg_rpath}"
        COMMAND mkdir -p ${GNUPKG_BINARY_PATH}
        COMMAND mkdir -p ${GNUPKG_INSTALL_PATH}
        )
    ADD_CUSTOM_COMMAND(
        TARGET ${_pkg_name}
        COMMENT "options: ${_pkg_options}"
        COMMAND export CC=${GNUPKG_CC}
        COMMAND export CXX=${GNUPKG_CXX}
        COMMAND export CFLAGS=${GNUPKG_CFLAGS}
        COMMAND export CXXFLAGS=${GNUPKG_CXXFLAGS}
        COMMAND ${GNUPKG_SOURCE_PATH}/configure ${_pkg_options}
        WORKING_DIRECTORY ${GNUPKG_BINARY_PATH}
        VERBATIM
        NO_ESCAPE_QUOTE
        )
ENDMACRO(CONFIG_GNU_PACKAGE)ui

3,編寫BUILD_GNU_PACKAGE宏,用來編譯上一步配置好的軟件包
MACRO(BUILD_GNU_PACKAGE _pkg_name _pkg_rpath)
    SET(GNUPKG_BINARY_PATH ${DS_BINARY_DIR}/gnupkg/${_pkg_rpath})
    SET(GNUPKG_BUILD_TARGETS ${GNUPKG_BUILD_TARGETS} ${_pkg_name})
    ADD_CUSTOM_TARGET(
        ${_pkg_name}
        COMMENT "building ${_pkg_name} in ${_pkg_rpath}"
        )
    ADD_CUSTOM_COMMAND(
        TARGET ${_pkg_name}
        COMMAND make
        COMMAND make install
        WORKING_DIRECTORY ${GNUPKG_BINARY_PATH}
        )
ENDMACRO(BUILD_GNU_PACKAGE).net

4,添加軟件包
SET(GNUPKG_CONFIG_TARGETS "")
SET(GNUPKG_BUILD_TARGETS "")
IF(DS_TARGET STREQUAL "X86")
    CONFIG_GNU_PACKAGE(libsigcxx_cfg 3rdParties/libsigc++-2.2.8 "--enable-shared=yes")
ENDIF(DS_TARGET STREQUAL "X86")blog

IF(DS_TARGET STREQUAL "SMP865X")
    CONFIG_GNU_PACKAGE(libsigcxx_cfg 3rdParties/libsigc++-2.2.8 "--host=mips")
ENDIF(DS_TARGET STREQUAL "SMP865X")ip

BUILD_GNU_PACKAGE(libsigcxx_build 3rdParties/libsigc++-2.2.8)
SET(DS_SIGC++_INCLUDE_DIR ${GNUPKG_INSTALL_PATH}/include/sigc++-2.0 ${GNUPKG_INSTALL_PATH}/lib/sigc++-2.0/include)
SET(DS_SIGC++_LIBRARY_DIR ${GNUPKG_INSTALL_PATH}/lib)
SET(DS_SIGC++_LIBS sigc-2.0)開發

5,添加一個總的配置全部package的目標
ADD_CUSTOM_TARGET(ds_gnupkg_config
    COMMENT "config done all gnu packages!"
    )
ADD_DEPENDENCIES(ds_gnupkg_config
    ${GNUPKG_CONFIG_TARGETS}
    )
6,添加一個總的編譯全部package的目標
ADD_CUSTOM_TARGET(ds_gnupkg_build
    COMMENT "built done all gnu packages"
    )
ADD_DEPENDENCIES(ds_gnupkg_build
    ${GNUPKG_BUILD_TARGETS}
    )

7,你能夠到所須要的地方用DS_SIGC++_INCLUDE_DIR , DS_SIGC++_LIBRARY_DIR , DS_SIGC++_LIBS等宏對sigc++進行調用

8,最後你能夠到DS_BINARY_DIR去執行
ccmake ..
make ds_gnupkg_config
make ds_gnupkg_build

備註:
CONFIG_GNU_PACKAGE這個宏在調用的時候會有問題。_pkg_options參數中內容常常會不止一個,在目前cmake-2.8.3版本及以前都不能將這個字符串正確的傳入到ADD_CUSTOM_COMMAND的COMMAND命令中。
如:你調用CONFIG_GNU_PACKAGE(libsigcxx_cfg 3rdParties/libsigc++-2.2.8 "--host=x86 --target=mips"),運行make ds_gnupkg_config VERBOSE=1後,會看到調用的shell命令轉換成了/home/Dev/DigitalSignage/3rdParties/libsigc++-2.2.8/configure --build=mips/ --host=x86,它將_pkg_options裏的空格轉義了!
翻看ADD_CUSTOM_COMMAND的用法後添加了一個參數VERBATIM到ADD_CUSTOM_COMMAND的最後,雖然不轉義了,但在_pkg_options先後添加了雙引號,變成了/home/Dev/DigitalSignage/3rdParties/libsigc++-2.2.8/configure "--build=mips --host=x86"。
再嘗試了各類方法(包括使用環境變量,LIST模式)以後,發現不管怎樣都不奏效。最後,下載了2.8.3版本的源碼,翻看了源碼後發現ADD_CUSTOM_COMMAND命令對COMMAND的後續內容作了處理,要麼加引號,要麼加轉義符,只是對一些shell的操做符如 ">" ,"|>"等沒有轉義。
據此,我修改了cmake2.8.3的源碼在ADD_CUSTOM_COMMAND中添加了一個操做符NO_ESCAPE_QUOTE,使得ADD_CUSTOM_COMMAND不作轉義和添加雙引號。NO_ESCAPE_QUOTE的位置等同VERBATIM。

 

附件:
BuildGNUPackage.cmake (http://u.115.com/file/f2c1b5d883)

cmake-2.8.3.modify.tar.bz2 ( http://u.115.com/file/f2862c7372 )

相關文章
相關標籤/搜索