Создание связывания общего объекта Python с помощью cmake, который зависит от внешних библиотек - PullRequest
6 голосов
/ 14 июня 2009

У нас есть файл c с именем dbookpy.c, который обеспечит привязку Python к некоторым функциям C.

Затем мы решили создать правильный .so с помощью cmake, но, похоже, мы делаем что-то не так в отношении связывания внешней библиотеки 'libdbook' в привязке:

CMakeLists.txt выглядит следующим образом:

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
)

Затем строим:

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

Пока все хорошо. Тест на 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

Хм. Ошибка компоновщика. Похоже, это не ссылка на 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

Нет, это не так. Правильная связь с libdbook выглядит так:

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

У кого-нибудь есть идеи, почему это не работает?

Большое спасибо.

Edd

Ответы [ 2 ]

3 голосов
/ 15 июня 2009

Вам необходимо связать dbookpy с dbook:

target_link_libraries(dbookpy dbook)

Добавим, что сразу после строки ADD_LIBRARY(dbookpy dbookpy) должен это сделать.

Я вижу, вы используете IMPORTED - справка для IMPORTED_LINK_INTERFACE_LIBRARIES гласит:

 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.

Таким образом, это означает, что dbook, который находится в / usr / local / lib, должен быть импортированной библиотекой:

 add_library(dbook SHARED IMPORTED)

Это действительно то, что вы хотели? Я имею в виду, что импортированные библиотеки созданы вне CMake, но включены как часть вашего исходного дерева. Библиотека dbook, кажется, установлена ​​или, по крайней мере, ожидается, что будет установлена. Я не думаю, что вам нужен импорт здесь - похоже, это проблема регулярных связей. Но это может быть просто побочным эффектом создания минимального примера для публикации здесь.

Судя по всему, чтобы отсортировать связанные библиотеки и каталоги ссылок, я бы, вероятно, использовал find_library(), который будет искать в разумных местах по умолчанию, таких как / usr / local / lib, и затем добавлять это к библиотеки ссылок.

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

Во всяком случае, похоже, что вы уже отсортировали его.

1 голос
/ 15 июня 2009

Спасибо за вашу помощь.

Вы правильно сказали, что IMPORTED, вероятно, не нужен. Добавление LINK_LIBRARIES (dbookpy dbook) действительно добавляет -ldbook к выполнению gcc, и это здорово.

Однако cmake, похоже, игнорирует LINK_DIRECTORIES и поэтому никогда не находит -ldbook:

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

Вот CMakeList в его нынешнем виде:

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
)

Есть идеи?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...