2009-06-14 13 views
5

Abbiamo un file c chiamato dbookpy.c, che fornirà un Python che associa alcune funzioni C.Costruire un binding di oggetti condivisi Python con cmake, che dipende dalle librerie esterne

successivo abbiamo deciso di costruire un .so adeguato con CMake, ma sembra che stiamo facendo qualcosa di sbagliato per quanto riguarda il collegamento 'libdbook' la libreria esterna nel legame:

Il CMakeLists.txt è la seguente:

PROJECT(dbookpy) 

FIND_PACKAGE(PythonInterp) 
FIND_PACKAGE(PythonLibs) 

INCLUDE_DIRECTORIES(${PYTHON_INCLUDE_PATH}) 
INCLUDE_DIRECTORIES("/usr/local/include") 
LINK_DIRECTORIES(/usr/local/lib) 
OPTION(BUILD_SHARED_LIBS "turn OFF for .a libs" ON) 

ADD_LIBRARY(dbookpy dbookpy) 
SET_TARGET_PROPERTIES(dbookpy PROPERTIES IMPORTED_LINK_INTERFACE_LIBRARIES dbook) 
SET_TARGET_PROPERTIES(dbookpy PROPERTIES LINKER_LANGUAGE C) 
#SET_TARGET_PROPERTIES(dbookpy PROPERTIES LINK_INTERFACE_LIBRARIES dbook) 
#SET_TARGET_PROPERTIES(dbookpy PROPERTIES ENABLE_EXPORTS ON) 
#TARGET_LINK_LIBRARIES(dbookpy LINK_INTERFACE_LIBRARIES dbook) 

SET_TARGET_PROPERTIES(dbookpy 
PROPERTIES 
    SOVERSION 0.1 
    VERSION 0.1 
) 

Poi costruire:

x31% mkdir build 
x31% cd build 
x31% cmake .. 
-- Check for working C compiler: /usr/bin/gcc 
-- Check for working C compiler: /usr/bin/gcc -- works 
-- Check size of void* 
-- Check size of void* - done 
-- Check for working CXX compiler: /usr/bin/c++ 
-- Check for working CXX compiler: /usr/bin/c++ -- works 
-- Configuring done 
-- Generating done 
-- Build files have been written to: /home/edd/dbook2/dbookpy/build 
x31% make 
Scanning dependencies of target dbookpy 
[100%] Building C object CMakeFiles/dbookpy.dir/dbookpy.o 
Linking C shared library libdbookpy.so 
[100%] Built target dbookpy 

Fin qui tutto bene. Test in Python:

x31% python 
Python 2.5.4 (r254:67916, Apr 24 2009, 15:28:40) 
[GCC 3.3.5 (propolice)] on openbsd4 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import libdbookpy 
python:./libdbookpy.so: undefined symbol 'dbook_isbn_13_to_10' 
python:./libdbookpy.so: undefined symbol 'dbook_isbn_10_to_13' 
python:./libdbookpy.so: undefined symbol 'dbook_sanitize' 
python:./libdbookpy.so: undefined symbol 'dbook_check_isbn' 
python:./libdbookpy.so: undefined symbol 'dbook_get_isbn_details' 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
ImportError: Cannot load specified object 

Hmmm. Errore del linker. Sembra che non stia collegando libdbook:

x31% ldd libdbookpy.so 
libdbookpy.so: 
     Start End  Type Open Ref GrpRef Name 
    05ae8000 25aec000 dlib 1 0 0  /home/edd/dbook2/dbookpy/build/libdbookpy.so.0.1 

No, non lo è. Un legame proprio libdbook assomiglia a questo:

x31% ldd /usr/local/bin/dbook-test 
/usr/local/bin/dbook-test: 
    Start End  Type Open Ref GrpRef Name 
    1c000000 3c004000 exe 1 0 0  /usr/local/bin/dbook-test 
    08567000 28571000 rlib 0 2 0  /usr/lib/libm.so.5.0 
    09ef7000 29efb000 rlib 0 1 0  /usr/local/lib/libdbook.so.0.1 
    053a0000 253d8000 rlib 0 1 0  /usr/lib/libc.so.50.1 
    0c2bc000 0c2bc000 rtld 0 1 0  /usr/libexec/ld.so 

Qualcuno ha tutte le idee perché questo non sta funzionando?

Molte grazie.

Edd

risposta

3

devi collegare dbookpy contro DBook:

target_link_libraries(dbookpy dbook) 

Aggiungendo che subito dopo la linea ADD_LIBRARY(dbookpy dbookpy) dovrebbe farlo.

vedo che si sta utilizzando importati - l'aiuto per IMPORTED_LINK_INTERFACE_LIBRARIES recita:

Lists libraries whose interface is included when an IMPORTED library target is 
linked to another target. The libraries will be included on the link line for 
the target. Unlike the LINK_INTERFACE_LIBRARIES property, this property 
applies to all imported target types, including STATIC libraries. This 
property is ignored for non-imported targets. 

Quindi questo significa che "DBook", che si trova in// local/lib usr, dovrebbe essere una libreria importata:

add_library(dbook SHARED IMPORTED) 

È davvero quello che volevi? Voglio dire, le librerie importate sono quelle che sono costruite fuori da CMake ma sono incluse come parte del tuo albero dei sorgenti. La libreria di dbook sembra essere installata o almeno dovrebbe essere installata. Non penso che tu abbia bisogno di importazioni qui - sembra essere un problema di collegamento regolare. Ma questo potrebbe essere solo un effetto collaterale della creazione di un esempio minimo da pubblicare qui.

Per i suoni di esso, per ottenere le librerie collegate e le directory dei collegamenti ordinate, probabilmente utilizzerei find_library(), che verrà visualizzato in posizioni predefinite come/usr/local/lib, quindi aggiungerlo al librerie di collegamenti.

find_library(DBOOK_LIBRARY dbook REQUIRED) 
target_link_libraries(dbookpy ${DBOOK_LIBRARY})  

In ogni caso, sembra che tu abbia ordinato ora.

+0

Hi rq, vedere la risposta di seguito. Grazie –

1

Grazie per il vostro aiuto.

Si ha ragione a dire che l'IMPORTAZIONE non è probabilmente necessaria. L'aggiunta di LINK_LIBRARIES (dbookpy dbook) aggiunge infatti -ldbook all'esecuzione gcc, quindi è fantastico.

Tuttavia CMake sembra ignorare LINK_DIRECTORIES, e così non trova mai -ldbook:

/usr/bin/gcc -fPIC -shared -o libdbookpy.so.0.1 "CMakeFiles/dbookpy.dir/dbookpy.o" -ldbook 
/usr/bin/ld: cannot find -ldbook 

Ecco la CMakeList così com'è:

PROJECT(dbookpy) 
SET(CMAKE_VERBOSE_MAKEFILE ON) 

OPTION(BUILD_SHARED_LIBS "turn OFF for .a libs" ON) 
ADD_LIBRARY(dbookpy dbookpy) 
SET_TARGET_PROPERTIES(dbookpy PROPERTIES LINKER_LANGUAGE C) 


FIND_PACKAGE(PythonInterp) 
FIND_PACKAGE(PythonLibs) 

INCLUDE_DIRECTORIES(${PYTHON_INCLUDE_PATH}) 
INCLUDE_DIRECTORIES(/usr/local/include) 
target_link_libraries(dbookpy dbook) 
LINK_DIRECTORIES("/usr/local/lib") 

SET_TARGET_PROPERTIES(dbookpy 
PROPERTIES 
     SOVERSION 0.1 
     VERSION 0.1 
) 

INSTALL(TARGETS dbookpy 
     LIBRARY DESTINATION lib 
) 

Tutte le idee?

+1

la risposta è aggiungere LINK_DIRECTORIES prima ADD_LIBRARY :) –

+0

Vale la pena notare che target_link_libraries si aspetta il nome del progetto e il nome della lib, non il percorso della lib (che un esempio che stavo usando aveva suggerito). In altre parole, la parte che verrebbe visualizzata accanto a -l, vale a dire. db (per Berkeley DB) che è libdb e si presenta come -ldb. – Asher

Problemi correlati