1

I use Swig.(Mac os 10.13)

My shell script:

swig -c++ -python -o example_wrap.cpp example.i

g++ -c -std=c++17  -fPIC example.cpp

g++ -c -std=c++17  -fPIC example_wrap.cpp -o example_wrap.o \
-I/usr/local/Cellar//python/3.7.2_2/Frameworks/Python.framework/Versions/3.7/include/python3.7m

ld -bundle -macosx_version_min 10.13 -flat_namespace \
-undefined suppress -o _example.so *.o

I spent enough time to seek how to create C++ dynamic library for Python, but I have never used the last line.Most often I create a library from an IDE. g++ -shared is more familiar, but it doesn't work. Many such errors appear:

Undefined symbols for architecture x86_64:
  "_PyArg_ParseTuple", referenced from:
      _wrap_printTree(_object*, _object*) in example_wrap.o

I know about this methods from Python.h. So, the questions are - how does the last line work(ld -bundle ...)? Are there other methods to create the dynamic library?How can I use g++ -shared?

nnuttertools
  • 131
  • 8
  • I wouldn't want to manually invoke the linker, this is error-prone and complicated. Maybe use `cmake` instead, it has good support for swig bindings. Besides, you need to link against the python library, e.g. `-lpython3.7` or something comparable. – lubgr Feb 16 '19 at 11:57
  • I know about `cmake`. It may not make sense, but I want to understand how it works if I create it manually. – nnuttertools Feb 16 '19 at 12:42
  • @lubgr, if you know good sources about cmake + swig, can you send it, please?) I can't write the same actions in `cmake`.The documentation is not very detailed and there are no examples :( – nnuttertools Feb 16 '19 at 17:57

1 Answers1

3

Here is a small CMakeLists.txt that should work for the example you posted:

cmake_minimum_required(VERSION 3.10) # change this to your needs

project(foo VERSION 0.0 LANGUAGES CXX C)

find_package(SWIG REQUIRED)
include(${SWIG_USE_FILE})

find_package(PythonLibs)

include_directories(${PYTHON_INCLUDE_PATH})
include_directories(${CMAKE_CURRENT_SOURCE_DIR})

set(CMAKE_SWIG_FLAGS "")

add_library(exampleImpl SHARED example.h example.cpp)
target_compile_features(exampleImpl PUBLIC cxx_std_17)

set_source_files_properties(example.i PROPERTIES CPLUSPLUS ON)

swig_add_library(example LANGUAGE python SOURCES example.i)
swig_link_libraries(example ${PYTHON_LIBRARIES} exampleImpl)

To make sure cmake uses the right python library, you can pass an appropriate option upon configure time, see here.

lubgr
  • 37,368
  • 3
  • 66
  • 117