swig and python3: surplus underscore
Question:
Using swig 2.0.8 and python 3.2, running
swig -python -modern -py3 -o mymodule_wrap.c mymodule.i
produces a wrapper file that has
# define SWIG_init PyInit__mymodule
in there (note the two underscores between PyInit and mymodule).
Importing fails with
python3 -c "import mymodule"
Traceback (most recent call last):
File "<string>", line 1, in <module>
ImportError: dynamic module does not define init function (PyInit_mymodule)
(note the single underscore).
Manually deleting the underscore in mymodule_wrap.c
and recompiling results in a working module.
In this question: SWIG and Python3 Import Error the python interpreter complained about not finding PyInit__module
.
What’s wrong?
Answers:
Make sure the extension module is named _mymodule.pyd
not mymodule.pyd
.
Explanation:
Given a SWIG .i
file containing the declaration:
%module mymodule
SWIG will generate two files:
- mymodule.py
- mymodule_wrap.c
mymodule.py
is imported into Python via import mymodule
and loads _mymodule.pyd
.
mymodule_wrap.c
contains an entry point function PyInit__mymodule
. This source file must be linked into the final _mymodule.pyd
.
Python’s import <module>
statement looks for:
<module>.pyd
with entry point PyInit_<module>
.
<module>.py
.
For a SWIG-generated extension, import mymodule
will load mymodule.py
, which loads _mymodule.pyd
and looks correctly for PyInit__mymodule
.
If the wrong extension name is used, import mymodule
will load mymodule.pyd
and look incorrectly for PyInit_mymodule
.
You can change this by passing -interface <mod>
to swig, as in swig -python -doxygen -py3 -c++ -cppext cpp -interface example_math interfaces/example_math.i
.
Then import example_math
works after compiling it like g++ -shared -fPIC src/example_math.cpp interfaces/example_math_wrap.cpp /Library/Frameworks/Python.framework/Versions/3.9/lib/libpython3.9.dylib -I/Library/Frameworks/Python.framework/Versions/3.9/include/python3.9 -o example_math.so
.
Using swig 2.0.8 and python 3.2, running
swig -python -modern -py3 -o mymodule_wrap.c mymodule.i
produces a wrapper file that has
# define SWIG_init PyInit__mymodule
in there (note the two underscores between PyInit and mymodule).
Importing fails with
python3 -c "import mymodule"
Traceback (most recent call last):
File "<string>", line 1, in <module>
ImportError: dynamic module does not define init function (PyInit_mymodule)
(note the single underscore).
Manually deleting the underscore in mymodule_wrap.c
and recompiling results in a working module.
In this question: SWIG and Python3 Import Error the python interpreter complained about not finding PyInit__module
.
What’s wrong?
Make sure the extension module is named _mymodule.pyd
not mymodule.pyd
.
Explanation:
Given a SWIG .i
file containing the declaration:
%module mymodule
SWIG will generate two files:
- mymodule.py
- mymodule_wrap.c
mymodule.py
is imported into Python via import mymodule
and loads _mymodule.pyd
.
mymodule_wrap.c
contains an entry point function PyInit__mymodule
. This source file must be linked into the final _mymodule.pyd
.
Python’s import <module>
statement looks for:
<module>.pyd
with entry pointPyInit_<module>
.<module>.py
.
For a SWIG-generated extension, import mymodule
will load mymodule.py
, which loads _mymodule.pyd
and looks correctly for PyInit__mymodule
.
If the wrong extension name is used, import mymodule
will load mymodule.pyd
and look incorrectly for PyInit_mymodule
.
You can change this by passing -interface <mod>
to swig, as in swig -python -doxygen -py3 -c++ -cppext cpp -interface example_math interfaces/example_math.i
.
Then import example_math
works after compiling it like g++ -shared -fPIC src/example_math.cpp interfaces/example_math_wrap.cpp /Library/Frameworks/Python.framework/Versions/3.9/lib/libpython3.9.dylib -I/Library/Frameworks/Python.framework/Versions/3.9/include/python3.9 -o example_math.so
.