【C++】linux下CMake生成動態連結庫,g++包含生成動態連結庫
一、前言
由於專案中要用到java呼叫C++的庫檔案,於是需要在linux下編譯連線生成動態庫,然後根據Recast官方包要先CMake生成編譯,然後在包含到自己實現的檔案,網上查了半天,坑爹沒有全面的,東拼西湊終於才明白原理,於是總結記錄分享如下。
二、CMake生成庫檔案
總的來說CMake生成過程不復雜,但是查到的資料都坑爹,廢話說了半天沒有說到要點,咱直奔主題,兩個步驟:
1)切到有CMakeList.txt檔案的資料夾下,執行CMake .命令(.是當前路徑)
2)執行make命令即可
然後就發現生成了libDetour.so檔案,這個就是自己的檔案依賴的recast庫。
當然這中間最重要的就是CMakeList.txt,這個檔案剪短,具體如下:
CMAKE_MINIMUM_REQUIRED(VERSION 2.6) SET(detour_SRCS Source/DetourAlloc.cpp Source/DetourCommon.cpp Source/DetourNavMesh.cpp Source/DetourNavMeshBuilder.cpp Source/DetourNavMeshQuery.cpp Source/DetourNode.cpp ) SET(detour_HDRS Include/DetourAlloc.h Include/DetourAssert.h Include/DetourCommon.h Include/DetourNavMesh.h Include/DetourNavMeshBuilder.h Include/DetourNavMeshQuery.h Include/DetourNode.h ) INCLUDE_DIRECTORIES(Include) ADD_LIBRARY(Detour ${detour_SRCS} ${detour_HDRS})
其中ADD_LIBRARY(Detour ${detour_SRCS} ${detour_HDRS})這個是裡面的需要加上SHARED表示動態庫檔案,而不是靜態庫檔案,方便自己的專案中包含進來。(PS昨天弄了好久,就是這個地方沒有改過來)
型別有三種: SHARED,動態庫STATIC,靜態庫MODULE,在使用dyld的系統有效,如果不支援dyld,則被當作SHARED對待。EXCLUDE_FROM_ALL引數的意思是這個庫不會被預設構建,除非有其他的元件依賴或者手工構建。具體更多引數和CMakeList.txt的編寫規範這裡就不多說了,可以參考CMake官方文件。
三、G++編譯生成最終的動態庫檔案
閒話少敘,先附上來命令:g++ -I /usr/local/jdk1.7.0_10/include/linux/ -I /usr/local/jdk1.7.0_10/include/ -I ./Include/ -L ./ -l Detour -fPIC -shared -o librecast.so PathFinding.cpp。
注意:要生成的是recast.so需要在java裡面載入的,然後是務必命名為librecast
System.load("recast");
還有就記得加上-L ./ -lDetour這個引數,否則就算正常編譯,執行的時候會報錯can not find symbol 某個函式的錯誤,不能正常執行。
這樣就搞定了。
接下來是具體的引數說明。
-shared 該選項指定生成動態連線庫(讓聯結器生成T型別的匯出符號表,有時候也生成弱連線W型別的匯出符號),不用該標誌外部程式無法連線。相當於一個可執行檔案。
-fPIC:表示編譯為位置獨立的程式碼,不用此選項的話編譯後的程式碼是位置相關的所以動態載入時是通過程式碼拷貝的方式來滿足不同程序的需要,而不能達到真正程式碼段共享的目的。
-L.:表示要連線的庫在當前目錄中
-l Detour:編譯器查詢動態連線庫時有隱含的命名規則,即在給出的名字前面加上lib,後面加上.so來確定庫的名稱
-I 專案中include包含的標頭檔案尋找路徑
...更多引數(請參閱G++編譯引數)
四、總結
其實還是自己的問題,在學校的時候沒有好好學C++編譯相關知識和在linux下的編譯相關知識,當年就稍微用IDE如微軟的Visual Studio隨便編譯了一下就以為自己會了額,真是年少啊不知天高地厚啊,現在就苦逼了。。其實也還好,弄過一遍就會了。。在此記錄提醒自己,學海無涯,多寫(學)點東西沒啥壞處。。。共勉。。
(全文完)