利用cmake構建C++應用程序

原文鏈接:https://cloud.tencent.com/developer/ask/114193

利用cmake構建C++應用程序

參考資料:

  1. cmake語法講解和入門示例
  2. 使用cmkae構建簡單qt工程
  3. 淺談 qmake 之 shadow build
  4. 如何編寫cmakelists.txt文件
  5. cmake參考手冊
  6. makefile經典教程

使用qt構建cmake程序的問題?出現“Parse error. Expected a command name, got unquoted argument with text”錯誤,這個是由於CMakeLists.txt文件的編碼被無意之中改變導致的。在qtcreator中選擇CMakeLists.txt文件,右鍵用binary格式打開:

img

正常的文件格式應該爲:

img

如果發現在cmake前面有其他的字符,比如ef,bf之類的,說明文件格式已經被修改爲其他格式了,此時需要修改文件的編碼格式!一種方法是在qtcreator中找到選項,文本編輯,行爲,文件編碼,將文件編碼設置爲UTF-8編碼格式;另一種方法是複製CMakeLists.txt中的文本內容,然後清空文本保存,會提示你空文本不能保存,此時輸入任意一個字符再保存,會發現前面的編碼識別字符已經不見了,此時再粘貼之前複製的文本回來,就再次找回了原來的編碼!

cmake構建C++應用程序示例=>

#指定cmake最小版本
cmake_minimum_required(VERSION 2.8)

#指定項目名稱
project(linux_rdma_server)

#設置C++編譯器和添加編譯器選項
set(CMAKE_CXX_COMPILER g++)
add_compile_options(-std=c++11)

#設置編譯模式
#set(CMAKE_BUILD_TYPE "Release")
#cmake -DCMAKE_BUILD_TYPE=Debug

#根據不同的編譯模式設置不同的生成路徑
IF (CMAKE_BUILD_TYPE MATCHES "Release")
    message("set CMAKE_BUILD_TYPE = Release")
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/release)
    set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/release)
ELSEIF (CMAKE_BUILD_TYPE MATCHES "MinSizeRel")
    message("set CMAKE_BUILD_TYPE = MinSizeRel")
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/minSizeRel)
    set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/minSizeRel)
ELSEIF(CMAKE_BUILD_TYPE MATCHES "RelWithDebInfo")
    message("set CMAKE_BUILD_TYPE = RelWithDebInfo")
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/relWithDebInfo)
    set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/relWithDebInfo)
ELSEIF(CMAKE_BUILD_TYPE MATCHES "Debug")
    message("set CMAKE_BUILD_TYPE = Debug")
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/debug)
    set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/debug)
ELSE()
    message("set CMAKE_BUILD_TYPE = Default")
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/default)
    set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin/default)
ENDIF()

#重置動態庫查找目錄
#如果使用了其他第三方庫,不必在linux系統安裝第三方庫
#拷貝動態庫文件到本地目錄,加上下面幾句即可解決!!!
set(CMAKE_SKIP_BUILD_RPATH FALSE)
set(CMAKE_BUILD_WITH_INSTALL_RPATH FALSE)
set(CMAKE_INSTALL_RPATH "$ORIGIN")
set(CMAKE_INSTALL_RPATH_USE_LINK_PATH TURE)

#設置自定義變量並根據變量參數設置不同的編譯選項
set(USE_CAMERA_TEST "YES")
IF (USE_CAMERA_TEST MATCHES "YES")
    message("Set USE_CAMERA_TEST = YES")
ELSE()
    message("set USE_CAMERA_TEST = NO")
ENDIF()

#添加預定義指令,每條指令前都需要加上-D,之後纔是預定義名稱
#預定義指令可以在程序中識別,使用#ifdef RDMA_DEBUG 即可!!!
add_definitions(-DRDMA_DEBUG)

#添加源文件路徑,使用cpplib替換./cpplib名稱
aux_source_directory(./cpplib cpplib)

#包含子項目路徑,子項目中的cmakelist.txt文件會被自動識別
add_subdirectory(cpplib)

#添加頭文件路徑
include_directories(./rdma_server)
include_directories(./cpplib)

#生成動態庫,包含所有需要編譯的文件,注意,這裏只需要包含.cpp文件,.h和.hpp文件可以選擇不包含
ADD_LIBRARY(rdma_server SHARED
    cpplib/cpplogger.cpp
    cpplib/cppfilesystem.cpp
    rdma_server/rdma_server.cpp)

#生成執行文件,同樣包含所有需要編譯的文件
ADD_EXECUTABLE(rdma_server_test
    rdma_server_test/main.cpp)

#將動態庫連接到指定的應用程序上,最緊密的依賴庫在前,間接依賴庫在後
target_link_libraries(rdma_server ibverbs rdmacm pthread)
target_link_libraries(rdma_server_test rdma_server ibverbs rdmacm pthread)

#拷貝文件或文件夾到目標程序生成目錄,執行cmake的時候就會執行拷貝
file(COPY "rdma_camera_test/copy_files" DESTINATION ${EXECUTABLE_OUTPUT_PATH})
file(COPY "rdma_camera_test/settings.cfg" DESTINATION ${EXECUTABLE_OUTPUT_PATH})

#注意鏈接動態庫設置:
#1) target_link_libraries(rdma_server ibverbs rdmacm pthread)
#2) target_link_libraries(rdma_server_test rdma_server ibverbs rdmacm pthread)
#這裏曾經踩過一個坑:只設置了2,未設置1,導致在運行時出現segment faul錯誤,
#排查原因是因爲rdma_server_test被設置了link庫,但rdma_server這個庫並沒有。
#因此我們需要給每個library和execute都設置like庫,否則運行時就會報告segment fault錯誤!!!

針對上面的cmake編寫的自動編譯生成bash文件=>

#!/bin/sh

if [ ! -d "build" ]; then
  echo "creat build directory"
  mkdir build
fi


echo "================= debug build ================="
if [ ! -d "build/debug" ]; then
  echo "creat debug directory"
  mkdir build/debug
fi
cd build/debug
cmake -D CMAKE_BUILD_TYPE=Debug ../..
make


cd ../..
echo "================= release build ================="
if [ ! -d "build/release" ]; then
  echo "creat release directory"
  mkdir build/release
fi
cd build/release
cmake -D CMAKE_BUILD_TYPE=Release ../..
make


echo "================= build complete ================="
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章