Como os sufixos do Python obtidos por imp.get_suffixes () são definidos (em particular no Debian Jessie)?

2

O comando

python -c "import imp; print(imp.get_suffixes())"

imprime uma lista de tuplas com sufixos usados ao importar módulos (consulte o documento de imp.get_suffixes ). Geralmente é simplesmente:

[('.so', 'rb', 3), ('module.so', 'rb', 3), ('.py', 'U', 1), ('.pyc', 'rb', 2)]

No entanto, no Debian jessie, há outro sufixo:

[('.x86_64-linux-gnu.so', 'rb', 3), ('.so', 'rb', 3), ('module.so', 'rb', 3), ('.py', 'U', 1), ('.pyc', 'rb', 2)]

e algumas extensões têm o sufixo .x86_64-linux-gnu.so , por exemplo, /usr/lib/python2.7/dist-packages/paraview/vtkCommonCorePython.x86_64-linux-gnu.so .

Eu gostaria de usar extensões que têm este sufixo com um Python que não é o sistema Python e que eu construí, mas não funciona porque este Python não tem o sufixo .x86_64-linux-gnu.so .

Então, pergunto-me como posso adicionar esse sufixo. Parece que não há nenhuma função como imp.add_suffix . Eu suspeito que isso é feito durante a construção do Python, mas eu me pergunto como ... Eu olhei para o código fonte dos pacotes Debian Python, mas não é simples e eu não consegui entender como funciona ...

    
por paugier 18.06.2015 / 15:52

2 respostas

1

Acabamos de ter o mesmo problema. Usando as informações fornecidas neste tópico, consegui ir mais longe.

Eu usei apt source python2.7 e debuild -b -uc -us para inspecionar em detalhes como o pacote oficial foi criado. A implementação de imp.get_suffixes() está em Python / import.c: 2940 imp_get_suffixes(...) , que lê sufixos da lista chamada _PyImport_Filetab . Essa lista, por sua vez, é basicamente _PyImport_DynLoadFiletab e _PyImport_StandardFiletab concatenada.

Tornou-se óbvio que _PyImport_DynLoadFiletab é o que deveríamos estar procurando, e sua definição varia para diferentes plataformas - elas estão em Python / dynload _ *. c. Em Python / dynload_shlib.c é:

const struct filedescr _PyImport_DynLoadFiletab[] = {
#ifdef __CYGWIN__
    {".dll", "rb", C_EXTENSION},
    {"module.dll", "rb", C_EXTENSION},
#else
#if defined(PYOS_OS2) && defined(PYCC_GCC)
    {".pyd", "rb", C_EXTENSION},
    {".dll", "rb", C_EXTENSION},
#else
#ifdef __VMS
    {".exe", "rb", C_EXTENSION},
    {".EXE", "rb", C_EXTENSION},
    {"module.exe", "rb", C_EXTENSION},
    {"MODULE.EXE", "rb", C_EXTENSION},
#else
#ifdef Py_DEBUG
    {"_d.so", "rb", C_EXTENSION},
    {"module_d.so", "rb", C_EXTENSION},
# ifdef MULTIARCH
    {"." MULTIARCH "_d.so", "rb", C_EXTENSION},
# endif
#endif
#ifdef MULTIARCH
    {"." MULTIARCH ".so", "rb", C_EXTENSION},
#endif
    {".so", "rb", C_EXTENSION},
    {"module.so", "rb", C_EXTENSION},
#endif
#endif
#endif
    {0, 0}
};

Está bem aqui: MULTIARCH , se você olhar o log de criação, será "x86_64-linux-gnu" (com aspas, por causa do - s). O valor é aparentemente de dpkg-architecture -qDEB_HOST_MULTIARCH , mas não verifiquei.

Mais importante, _PyImport_DynLoadFiletab não se parece com isso originalmente em dynload_shlib.c, foi corrigido. Portanto, para obter o mesmo comportamento, é necessário aplicar um patch, pelo menos, adicionar a parte {"." MULTIARCH ".so", ...} . No meu caso, o patch deste arquivo (dynload_shlib.c) parece suficiente.

    
por 16.10.2018 / 19:40
0

Você deve compilar seu não-sistema-python depois de configurá-lo com a mesma configuração do python do Debian. Uma maneira de "recuperar" isso é do módulo sysconfig .

python -c "import sysconfig; print(sysconfig.get_config_vars()['CONFIG_ARGS'])"

apresenta algo como:

'--enable-shared' '--prefix=/usr' '--enable-ipv6' '--enable-unicode=ucs4' '--with-dbmliborder=bdb:gdbm' '--with-system-expat' '--with-system-ffi' '--with-fpectl' 'CC=x86_64-linux-gnu-gcc' 'CFLAGS=-D_FORTIFY_SOURCE=2 -g -fstack-protector --param=ssp-buffer-size=4 -Wformat -Werror=format-security ' 'LDFLAGS=-Wl,-Bsymbolic-functions -Wl,-z,relro'

que você teria que passar para ./configure no diretório de origem do Python.

    
por 18.06.2015 / 16:15