[CMake] python wrappers through xcode

Antoine PREVOT tonio_lesec at yahoo.fr
Wed Jul 30 15:39:25 EDT 2008


Hi,

First of all, english is not my native language, so I hope i'll be 
understandable. Don't hesitate to correct me (it's the only way to 
progress), or ask for rephrasing if it's not. And since it's my first 
post here, i'll be happy to produce some personal introduction if needed !

- Environnement :

OSX Tiger (darwin 8.11.1) - XCode 2.4.1 - CMake 2.4 - SWIG 1.3.36 hand 
compiled from standard tgz.

- Project context (optional) :

To make it simple, I am programming a fluid simulation library. It's 
goal is to produce a liquid/smoke surface behavior (a mesh and a 
pressure/density/velocity field). This library is meant to be called 
through two main ways : direct library link (opengl test/demo 
applications), and python wrappers (Maya/Renderman scripted plug-ins).

To be totally independent, the fluid simulator only produces basic 
topology and "aspect aims" in a gegneric structure (a render heap 
similar to the scene tree internally implemented by Maya). This 
structure is declared/handled in a separate library.

 From here, an opengl program only have to read this heap and compute 
corresponding GL primitives. A maya plug-in will only retrieve the mesh 
topology (vectors/edges/faces) to build it's own MFnMesh object. A 
renderman interface will only read density values (since renderman is 
able to generate implicit surfaces alone) etc.

It's, obviously, a cross-platform project ... but i'll focus on xcode 
for now. The reason i'm describing all this annoying stuff is that I 
still don't know if it's the proper way to make things, but a 
svn/cmake/swig combination seemed appropriated.

- What I tried and didn't happen to succeed (here comes the flop) :

The step I'm stuck in, is the way to automatically generate python 
wrappers through CMake build / XCode compilation.

Consider I have a root project, a toolkit library, a subpart of this lib 
(utils), and an existing not-so-c++-style-but-well-named example.cpp 
file in this subpart I want to expose to python. The project tree could be :
trunk\CMakeLists.txt
trunk\src\CMakeLists.txt
trunk\src\mysdk\CMakeLists.txt
trunk\src\mysdk\utils\example.cpp
trunk\src\mysdk\utils\example.i
(pretty simple, doesn't it ?)

Root CMakeLists contains platform specific operations, project 
configuration and libraries research, especialy python and swig :

******************** trunk\CMakeLists.txt
...
# common issue on osx while using non standard compilation
# SWIG_DIR must be manually specified
SET(SWIG_DIR "/usr/local")
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 "-c++")
...

Sources CMakeLists will only point on subprojects, libraries etc. :

******************** trunk\src\CMakeLists.txt
SUBDIRS(
   mysdk
)

Library CMakeList will declare it's own contents and resources, and 
eventually python wrappers (here we are) :

******************** trunk\src\mysdk\CMakeLists.txt
SET(MYSDK_UTILS_SOURCES
   utils/example.cpp
   utils/example.i
)
SET_SOURCE_FILES_PROPERTIES(utils/example.i PROPERTIES CPLUSPLUS ON)
SET_SOURCE_FILES_PROPERTIES(utils/example.i PROPERTIES SWIG_FLAGS 
"-includeall")
SET(MYSDK_SOURCES ${MYSDK_UTILS_SOURCES})
SOURCE_GROUP(Utils FILES ${MYSDK_UTILS_SOURCES})
ADD_LIBRARY(mysdk ${MYSDK_SOURCES})
SWIG_ADD_MODULE(example python utils/example.i utils/example.cpp)
SWIG_LINK_LIBRARIES(example ${PYTHON_LIBRARIES})

example.cpp is a simple function, c/p powered :

******************** trunk\src\mysdk\utils\example.cpp
int cube(int n)
{
   return (n * n * n);
}

example.i is the corresponding wrapper declaration :

******************** trunk\src\mysdk\utils\example.i
%module example
%{
extern int cube( int n );
%}
%include example.cpp


Manually swigged/compiled (see 
http://www.penzilla.net/tutorials/python/swig/), everything is fine (it 
would be a shame) :
# example_wrap.cxx creation
/usr/local/bin/swig -python -c++ example.i
# compilation
gcc -c example.cpp example_wrap.cxx -I 
/Library/Frameworks/Python.framework/Versions/2.4/include/python2.4/
# link
ld -bundle -flat_namespace -undefined suppress -o _example.so example.o 
example_wrap.o

python can access this module and use the wrapped function :
me#> python
 >>> import _example
 >>> _example.cube(2)
8
 >>>

- The issue

The xcode project generated is quite strange (ccmake -G"Xcode") :
1/ example.cpp & example.i have duplicated entries (but it's definitely 
the same file appearing twice)
2/ an extra _example library is created (besides the mmsdk one), 
targeting an _example.so output (fine!), but this lib :
	- contains an empty Utils folder (wow, what a coincidence :')
	- attempts to source an examplePYTHON_wrap.cxx file (which obviously 
doesnt exist)

Manually creating this cxx file with swig from the original sources 
location, then moving it to the generated build/macosx-xcode/[...] 
folder eventually do the job, and I could write a corresponding 
cross-platform script to do it but ... whats the point on using CMake 
that way ? :-/

I guess i'm missing something so big I can't see it, just here, right 
under my nose, but i had so much headaches having svn, cmake and swig up 
in this crappy undocumented os that I can't figure out what is happening 
now. I wish I were still on my sweet old debian  :)

I will take any advice, throught, even rtfm-style atomization, thanks in 
advance !

Tonio
If you can read this, you don't need glasses.



More information about the CMake mailing list