CMake 工程調用 Makefile 編譯項目


本文主要介紹如何將一個依賴 Makefile 項目(MIDG)移植到 CMake 上。

首先介紹項目文件結構,文件主要由三個目錄組成

  1. 3rdParty
  2. include
  3. src

其中,3rdParty 中包含兩個外部函數庫,即 MetisParMetis,生成兩個靜態鏈接庫 libmetis.alibparmetis.asrc 包含項目所有源程序, include 則包含了全部頭文件。

因此,我們在根目錄下 cmake 配置文件內容如下

cmake_minimum_required(VERSION 3.1)
project(DGOM)

set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS}")

set(CMAKE_C_COMPILER /usr/local/bin/mpicc)
set(CMAKE_CXX_COMPILER /usr/local/bin/mpicxx)


# 3rdParty library
# Build with original makefile
set(METIS_LIBRARY ${CMAKE_CURRENT_SOURCE_DIR}/lib/libmetis.a)
set(PARMETIS_LIBRARY ${CMAKE_CURRENT_SOURCE_DIR}/lib/libparmetis.a)

add_custom_target(build_metis ALL
        COMMAND ${CMAKE_MAKE_PROGRAM}
        WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/3rdParty/ParMetis-3.1/METISLib/
        COMMENT "Original metis makefile target")

add_custom_target(build_parmetis ALL
        COMMAND ${CMAKE_MAKE_PROGRAM}
        WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/3rdParty/ParMetis-3.1/ParMETISLib/
        COMMENT "Original parmetis makefile target")

add_library(metis STATIC IMPORTED)
add_library(parmetis STATIC IMPORTED)

set_property(TARGET metis APPEND PROPERTY IMPORTED_CONFIGURATIONS NOCONFIG)
set_target_properties(metis PROPERTIES IMPORTED_LOCATION_NOCONFIG "${METIS_LIBRARY}")

set_property(TARGET parmetis APPEND PROPERTY IMPORTED_CONFIGURATIONS NOCONFIG)
set_target_properties(parmetis PROPERTIES IMPORTED_LOCATION_NOCONFIG "${PARMETIS_LIBRARY}")

add_dependencies(metis build_metis)
add_dependencies(parmetis build_parmetis)

# source file
add_subdirectory(src)
  1. set(CMAKE_C_COMPILER mpicc)set(CMAKE_CXX_COMPILER mpicxx) 負責選擇項目編譯器,本項目中選擇 mpich2
  2. Metis Parmetis 第三方庫采用原始 makefile 編譯,將編譯好的靜態庫文件添加到項目中

1. 3rdParty

3rdParty 目錄如下

./
└── ParMetis-3.1
    ├── METISLib
    ├── Manual
    └── ParMETISLib

METISLibParMETISLib 分別為兩個不同的網格划分庫。原始make命令分別進入兩個項目所在目錄使用make命令即可。因此,在主目錄 CMakeLists.txt 中調用 make 命令編譯庫函數,主要步驟如下:

1.1. 增加自定義編譯方法

add_custom_target(build_metis ALL
        COMMAND ${CMAKE_MAKE_PROGRAM}
        WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/3rdParty/ParMetis-3.1/METISLib/
        COMMENT "Original metis makefile target")

add_custom_target(build_parmetis ALL
        COMMAND ${CMAKE_MAKE_PROGRAM}
        WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/3rdParty/ParMetis-3.1/ParMETISLib/
        COMMENT "Original parmetis makefile target")

add_custom_target 通過用戶給定的指令來增加一個新的編譯目標。ALL 代表該目標添加到默認編譯目標中,因此每次編譯都會執行。

1.2. 增加兩個編譯目標

這兩個目標為外部庫 IMPORTED,而非項目自己編譯的

add_library(metis STATIC IMPORTED)
add_library(parmetis STATIC IMPORTED)

set_property(TARGET metis APPEND PROPERTY IMPORTED_CONFIGURATIONS NOCONFIG)
set_target_properties(metis PROPERTIES IMPORTED_LOCATION_NOCONFIG "${METIS_LIBRARY}")

set_property(TARGET parmetis APPEND PROPERTY IMPORTED_CONFIGURATIONS NOCONFIG)
set_target_properties(parmetis PROPERTIES IMPORTED_LOCATION_NOCONFIG "${PARMETIS_LIBRARY}")

1.3. 將編譯目標與編譯方法聯系

確保首先執行編譯過程

add_dependencies(metis build_metis)
add_dependencies(parmetis build_parmetis)

2. 項目源文件

源文件編譯時候需要頭文件路徑,並且與第三方庫進行鏈接

set(SRC_LIST
        Mesh2d.c Utils.c LoadBalance2d.c FacePair2d.c
        ParallelPairs.c BuildMaps2d.c StartUp2d.c
        MaxwellsRun2d.c MaxwellsMPI2d.c MaxwellsDriver2d.c
        MaxwellsRHS2d.c InitCPU2d.c)

add_executable(DGOM2 ${SRC_LIST})

include_directories("../include")
target_link_libraries(DGOM2 metis parmetis)

2.1. 增加可執行程序

add_executable(DGOM2 ${SRC_LIST})

2.2. 給出頭文件路徑

include_directories("../include")

2.3. 給定鏈接第三方函數庫

target_link_libraries(DGOM2 metis parmetis)


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM