Cmake 實現debug和release lib依賴項處理
一、說明
最近用cmake開發東西,編譯vs時候,發現debug和release版本的lib庫的依賴項問題,故此小結一下。若有不對之處,還請看官多多指教。
使用的工程有自己編寫的工程,也有借用第三方庫的工程,還有沒有辦法找到原始碼的,只有dll和lib庫,沒有區分debug和release 版本的。
所以還是分開說,一種自己工程庫,一種是第三方庫。在寫完cmake程式碼,生成vs後,都可以自動的新增連結庫,debug和release版本涇渭分明。
二、自己工程之間的引用
先說,自己編寫的工程,工程直接的相互呼叫,這個就不用多說了。Cmake還是要呼叫target_link_libraries來連結自己的想要連結的動態庫。
但是需用做些設定,就可以自動的區分debug和release版本了。
首先,需實現cmake定義如下:
#這個就是定義各個版本對應的字尾,例如d,debug版本字尾,當然你想定義為其他, #自己修改這塊就可以了。
SET(CMAKE_DEBUG_POSTFIX "d" CACHE STRING "add a postfix, usually d on windows")
SET(CMAKE_RELEASE_POSTFIX "" CACHE STRING "add a postfix, usually empty on windows")
SET(CMAKE_RELWITHDEBINFO_POSTFIX "rd" CACHE STRING "add a postfix, usually empty on windows")
SET(CMAKE_MINSIZEREL_POSTFIX "s" CACHE STRING "add a postfix, usually empty on windows")
# Set the build postfix extension according to what configuration is being built.
IF (CMAKE_BUILD_TYPE MATCHES "Release")
SET(CMAKE_BUILD_POSTFIX "${CMAKE_RELEASE_POSTFIX}")
ELSEIF (CMAKE_BUILD_TYPE MATCHES "MinSizeRel")
SET(CMAKE_BUILD_POSTFIX "${CMAKE_MINSIZEREL_POSTFIX}")
ELSEIF(CMAKE_BUILD_TYPE MATCHES "RelWithDebInfo")
SET(CMAKE_BUILD_POSTFIX "${CMAKE_RELWITHDEBINFO_POSTFIX}")
ELSEIF(CMAKE_BUILD_TYPE MATCHES "Debug")
SET(CMAKE_BUILD_POSTFIX "${CMAKE_DEBUG_POSTFIX}")
ELSE()
SET(CMAKE_BUILD_POSTFIX "")
ENDIF()
以上程式碼我們是在外層的CMakeLists.txt中實現的。
接著下來cmake程式碼是在內層的cMakeLists.txt中實現。主要是使用外層定義的東西。
Cmake程式碼如下:
# Set the library extension according to what configuration is being built.
IF(CMAKE_DEBUG_POSTFIX)
SET(CMAKE_CXX_FLAGS_DEBUG
"${CMAKE_CXX_FLAGS_DEBUG} -DRW_LIBRARY_POSTFIX=${CMAKE_DEBUG_POSTFIX}")
ENDIF()
IF(CMAKE_RELEASE_POSTFIX)
SET(CMAKE_CXX_FLAGS_RELEASE
"${CMAKE_CXX_FLAGS_RELEASE} -DRW_LIBRARY_POSTFIX=${CMAKE_RELEASE_POSTFIX}")
ENDIF()
IF(CMAKE_RELWITHDEBINFO_POSTFIX)
SET(CMAKE_CXX_FLAGS_RELWITHDEBINFO
"${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -DRW_LIBRARY_POSTFIX=${CMAKE_RELWITHDEBINFO_POSTFIX}")
ENDIF()
IF(CMAKE_MINSIZEREL_POSTFIX)
SET(CMAKE_CXX_FLAGS_MINSIZEREL
"${CMAKE_CXX_FLAGS_MINSIZEREL} -DRW_LIBRARY_POSTFIX=${CMAKE_MINSIZEREL_POSTFIX}")
ENDIF()
其中的RW_LIBRARY_POSTFIX是我們工程相關的名稱,你們可以自己設定。在工程屬性的出現,如下所示:
三、第三方庫
關於第三方庫,情況比較複雜。有原始碼的,沒有原始碼的,靜態的,動態的,只有release,沒有debug的。我們現在做的是要求,至少有release版本的的lib庫。如沒有就不會新增到所需的工程的依賴項中。
因為第三方庫,在專案組中,各自的工程各自知道需用什麼第三方庫,所以就寫了一個cmake的巨集定義來實現。
下面是cmake原文程式碼:
#link library for debug and release by yourself.
MACRO(RW_LINK_LIBRARY BASE_LIBRARY_NAME DEBUGSUFFIX EXSUFFIX)
set(DEBUG_LIB ${PROJECT_SOURCE_DIR}/${BASE_LIBRARY_NAME}${DEBUGSUFFIX})
set(RELEASE_LIB ${PROJECT_SOURCE_DIR}/${BASE_LIBRARY_NAME}${EXSUFFIX})
IF(EXISTS ${RELEASE_LIB})
<span style="white-space:pre"> </span>target_link_libraries(${PROJECT_NAME} optimized ${RELEASE_LIB})
<span style="white-space:pre"> </span>IF(EXISTS ${DEBUG_LIB})
<span style="white-space:pre"> </span> target_link_libraries(${PROJECT_NAME} debug ${DEBUG_LIB})
<span style="white-space:pre"> </span>ELSE()
<span style="white-space:pre"> </span> target_link_libraries(${PROJECT_NAME} debug ${RELEASE_LIB})
<span style="white-space:pre"> </span>ENDIF(EXISTS ${DEBUG_LIB})
ENDIF(EXISTS ${RELEASE_LIB})
ENDMACRO()
MACRO(RW_LINK_3RD_PART_LIBRARY FULL_LIBRARY_DEBUGNAME FULL_LIBRARY_RELEASENAME)
IF(EXISTS ${FULL_LIBRARY_RELEASENAME})
target_link_libraries(${PROJECT_NAME} optimized ${FULL_LIBRARY_RELEASENAME})
IF(NOT EXISTS ${FULL_LIBRARY_DEBUGNAME})
target_link_libraries(${PROJECT_NAME} debug ${FULL_LIBRARY_RELEASENAME})
ELSE()
target_link_libraries(${PROJECT_NAME} debug ${FULL_LIBRARY_DEBUGNAME})
ENDIF(NOT EXISTS ${FULL_LIBRARY_DEBUGNAME})
ENDIF(EXISTS ${FULL_LIBRARY_RELEASENAME})
ENDMACRO()
巨集的使用方式為:
第一個巨集的使用在對應的工程下,lib庫可以寫相對路徑。
RW_LINK_LIBRARY(free_image/FreeImage "d.lib" ".lib")
第一個引數為含路徑名稱的lib庫名稱,後面分別為debug和release版本的區分。
此定義還不是很完善,以後可能修改為只新增不同的部分,比如:
RW_LINK_LIBRARY(free_image/FreeImage "d" "") 內部自動來識別andriod 或ios或msvc等。
第二個巨集的用法為:
RW_LINK_3RD_PART_LIBRARY(${GDAL_LIBRARY_DEBUG} ${GDAL_LIBRARY})
其中裡面寫的是兩個lib庫的路徑變數。
兩個巨集定義的原則均為,當沒有debug版本的lib庫時候,使用release版本的lib庫。
ps:
Cmake也是邊做邊學,若有不足之處,還請多多包含。
其中,也有實現了功能,而不知所以的地方。
若有問題,請不吝指正。
---------------------
作者:cartzhang
來源:CSDN
原文:https://blog.csdn.net/cartzhang/article/details/29193091
版權宣告:本文為博主原創文章,轉載請