Python - Py_Initialize unresolved during compilation
gcc, python, static-libraries, unresolved-external
Solution
The order matters! More specifically, the order in the arguments for gcc matters. More specifically, if a `bar` object uses a function `bluh` from library `bleh`, then the order `-lbleh bar.o` is problematic because it provides no reason to gcc look for the function `bluh` in `bleh`. On the other hand, when you use `bar.o -lbleh` then gcc knows you are referring to `bluh` and when it gets to handle `-lbleh` it tries to resolve the dependence. This is quickly mentioned at http://gcc.gnu.org/onlinedocs/gcc/Link-Options.html. As a rule, always specifies libraries after your objects.
To reproduce your problem, create a file `a1.c` as in:
#include "Python.h"
int main()
{
Py_Initialize();
return 0;
}
Now compile with `gcc -static -I/usr/include/python2.7 -L/usr/lib/python2.7/config/ -lpython2.7 -ldl -lm -lutil -lz -pthread -o a1 a1.c`. This gives the undefined reference to `Py_Initialize`. Of course you have to change the paths to match your installation.
Now, instead, compile with `gcc -static -I/usr/include/python2.7 -L/usr/lib/python2.7/config/ -o a1 a1.c -lpython2.7 -ldl -lm -lutil -lz -pthread` and it works (ignoring the possible many warnings, which is a different matter).
Problem
I have statically compiled Python2.7 without any error. To test my build, I use the following snippet: ``` #include "Python.h" int main() { Py_Initialize(); } ``` And I am compiling it like this: ``` $ gcc -static -I/path/to/python/header -L/path/to/my/staticpythonlib \ -lpython2.7 -ldl -l_all_other_needed_lib /tmp/my_previous_snippet.c -o myouput ``` However, an error occured. gcc claims the famous `undefined reference`. test.c:(.text+0x1): Undefined reference to 'Py_Initialize' Curiously I used gcc with the verbosity flag (I won't paste the result here) and the compiler says, it's using my libpython, but couldn't find the reference. So I listed the symbols of my static python2.7 library : ``` $ nm /path/to/pythonlib |grep Py_Initialize frozenmain.o U Py_Initialize pythonrun.o 0000009e9 T Py_Initialize pythonrun.o 000000052 T Py_Initialize_Ex main.o U Py_Initialize ``` We can see, that `Py_Initialize` is correctly referenced in pythonrun.o. However i don't know how the compiler chose the correct object file. My questions are : - How can I be sure, that gcc uses the correct object file in my .a lib? - Is there anything wrong on my compilation options? Thanks for your help.