2013-02-25 182 views
4

我有一個Makefile對於C++ Linux項目:Makefile文件 - 無法找到共享庫

MODE ?= dbg 
DIR = ../../../../../somdir/$(MODE) 

SRC_FILES = a.cpp b.cpp 
H_FILES = a.h 

LDFLAGS += -L$(DIR)/lib/linux '-Wl,-R$$ORIGIN' 
CPPFLAGS = -I$(DIR)/include 
LIBRARIES = -lsomeso 

ifeq (rel, $(MODE)) 
    CFLAGS = -Wall -g -DNDEBUG 
else 
    CFLAGS = -Wall -ansi -pedantic -Wconversion -g -DDEBUG -D_DEBUG 
endif 

sample: $(SRC_FILES) $(H_FILES) Makefile 
    g++ $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) $(LIBRARIES) $(SRC_FILES) -o sample 

當我運行「製作」它建立項目,沒有任何錯誤。 但是當我運行該項目,它抱怨說:

error while loading shared libraries: libsomeso.so: cannot open shared object file: No such file or directory 

,我給在DIR路徑去共享對象舉行(相對到makefile文件被放置)的文件夾,如果它是爲什麼在製作過程中沒有抱怨?

有人知道我錯過了什麼嗎?

感謝 馬特

回答

3
LDFLAGS += -L$(DIR)/lib/linux '-Wl,-R$$ORIGIN' 

上面的應該是:

LDFLAGS += -L$(DIR)/lib/linux -Wl,-R$(DIR)/lib/linux '-Wl,-R$$ORIGIN' 

也就是說,對於每個非標準動態庫的位置-L相應-Wl,-R應該被指定。需要$ORIGIN來定位動態庫相對於可執行文件,不知道你是否需要它在這裏。

人們經常會推薦使用LD_LIBRARY_PATH。在我看來,這是一個不好的建議,因爲它會使部署更加複雜。

2

當你運行你的應用程序中,libsomeso.so位置應在LD_LIBRARY_PATH環境變量。試運行的程序是這樣的:

LD_LIBRARY_PATH="path_to_libsomeso_so:$LD_LIBRARY_PATH" myprogram 

這裏path_to_libsomeso_so是一個目錄其中libsomeso.so所在完整路徑,myprogram是你的可執行程序。請注意,您應該指定包含libsomeso.so的目錄的路徑,而不是libsomeso.so文件本身。

1

麻煩不在編譯期間。一切都很好。運行時出現問題。

的確,您的程序已經與共享對象庫鏈接。因此,在運行時,它需要加載這個共享對象文件。在編譯過程中,您將指示編譯器在-L標誌處的文件所在的位置。

對於運行時,您必須將LD_LIBRARY_PATH環境變量設置爲指向libsomeso.so文件所在的目錄。

或者,你可以把這個文件在這些共享的目標文件中搜索標準目錄之一:/usr/local/lib/usr/lib/lib,但是這應該是你會爲你的庫的最終分佈式版本做什麼。

0

正如Maxim Egorushkin所說,LD_LIBRARY_PATH是一個不錯的選擇。同時,使用-L$(your lib path) -l$(your lib name) gcc/g ++參數來鏈接共享庫不是一個好的選擇。因爲在構建exe文件之後,你應該告訴exe共享庫目錄在哪裏。默認情況下,可執行文件僅在/usr/lib/usr/local/lib搜索共享庫。雖然,您已經告訴makefile生成可執行文件時共享庫的位置。但是當你執行這個exe文件時,它們是不同的。 但是,鏈接靜態庫沒有這樣的問題。

因此,處理您的問題的最好方法是改變您鏈接自定義共享文件的方式。像這樣:

DYNAMIC_LIB_DIR = ../lib (your lib path ,this is a example) 

OBJLIBS = xxx.so (your lib name) 

gcc/g++ -o exe_name sourcefile/object_file $(DYNAMIC_LIB_DIR)/$(OBJLIBS) 
0

刷新動態庫緩存!

將自定義非標準庫添加到/usr/local/lib後,首先檢查/usr/local/lib是否在/etc/ld.so.conf.d/libc.conf下面列出。

然後,玩完一個動態連接庫緩存刷新:

$ sudo ldconfig