2010-09-14 7 views
6

Recientemente actualicé desde Python 2.5 a 2.7 (probé 2.6 durante mis molestias) y aunque todo funciona bien desde la línea de comandos o en el servidor de ejecución de Django, mod_wsgi no puede cargar ningún módulo que contenga DLL (pyd) creado con MSVC.¿Por qué las DLL de Python creadas con MSVC no se cargan con mod_wsgi?

Por ejemplo, si construyo mis propias versiones de pycrypto o lxml entonces voy a obtener el siguiente error sólo de mod_wsgi:

ImportError at/
DLL load failed: The specified module could not be found. 

Incluso los binarios oficiales PIL dejarán de importar el módulo _imaging C en mod_wsgi pero ese puede ser otro problema.

Sin embargo, si uso una versión de pycrypto creada con MinGW desde algún lugar como http://www.voidspace.org.uk/python/modules.shtml#pycrypto, entonces importará bien incluso en mod_wsgi. No creo que esta solución sea satisfactoria, ya que la razón por la que actualicé Python fue para evitar tener que buscar binarios precompilados y no puedo crearlos yo mismo porque MinGW falla> 50% del tiempo para mí.

Edit2: me di cuenta de esto en python27/lib/distutils/msvc9compiler.py en las líneas 680-705:

try: 
    # Remove references to the Visual C runtime, so they will 
    # fall through to the Visual C dependency of Python.exe. 
    # This way, when installed for a restricted user (e.g. 
    # runtimes are not in WinSxS folder, but in Python's own 
    # folder), the runtimes do not need to be in every folder 
    # with .pyd's. 
    manifest_f = open(manifest_file) 
    try: 
     manifest_buf = manifest_f.read() 
    finally: 
     manifest_f.close() 
    pattern = re.compile(
     r"""<assemblyIdentity.*?name=("|')Microsoft\."""\ 
     r"""VC\d{2}\.CRT("|').*?(/>|</assemblyIdentity>)""", 
     re.DOTALL) 
    manifest_buf = re.sub(pattern, "", manifest_buf) 
    pattern = "<dependentAssembly>\s*</dependentAssembly>" 
    manifest_buf = re.sub(pattern, "", manifest_buf) 
    manifest_f = open(manifest_file, 'w') 
    try: 
     manifest_f.write(manifest_buf) 
    finally: 
     manifest_f.close() 
except IOError: 
    pass 

Esto probablemente explica por qué todo funciona desde la línea de comandos, pero no en mod_wsgi. Comentar todo esto parece solucionar el problema, pero no parece la solución adecuada. La pregunta ahora es dónde poner msvcr90.dll para que Apache pueda usarlo? Observé que la carpeta bin de Apache contiene msvcr70.dll y msvcr80.dll pero poner 90 allí no funciona.

+1

Saltarse eliminar manifiesta trabajó para mí demasiado bajo IIS con pyodbc – lambacck

Respuesta

1

Si bien no sé nada sobre mod_wsgi, me atrevo a adivinar que la razón más probable es la falta de dependencias de tiempo de ejecución. Es posible que desee inspeccionar su MSVC-build con Dependency Walker que se envía con MSVC (por ejemplo, en MSVC 2005, está ubicado en \ Common7 \ Tools \ Bin \ Depends.Exe). Le mostrará qué archivos DLL son requeridos por un archivo binario.

Como otra solución, debería ser posible construir sus módulos con tiempo de ejecución enlazado estáticamente (vea Propiedades del proyecto -> C/C++ -> Generación de código -> Runtime - elija "Multithreaded" (no "DLL multiproceso"); o, si está construyendo desde la línea de comando, asegúrese de que se use /MT en lugar de /MD). Sin embargo, puede haber problemas si los elementos dependientes del tiempo de ejecución (por ejemplo, objetos FILE *) cruzan el límite del módulo.

UPD Si tiene instalado correcta Redist VC, la razón puede ser un problema con la configuración SxS (es decir manifiesta de .pyd en sí está mal o falta, o conflictos con el manifiesto de la aplicación que carga el .pyd) Puede usar la utilidad sxstrace para ver qué está sucediendo exactamente. Ver Diagnosing SideBySide failures.

Además, ¿intentó la vinculación estática del tiempo de ejecución? O mejor aún, verifique cuáles son los requisitos de su proceso de host.

+0

Se están perdiendo Msvcr90.dll (y GPSVC y IESHIMS). Puse MSVCR90.DLL junto con AES.pyd y Dependency Walker pasa, pero Apache da un error de tiempo de ejecución. Tengo el redireccionamiento VC y MSVCR90.dll está en varias carpetas en C: \ Windows \ winsxs. ¿Algunas ideas? –

+0

Edité la pregunta original para mostrar cómo se construyó realmente AES.pyd. Hubiera sido destrozado como un comentario. –

+0

@Kyle MacFarlane - He editado mi respuesta en respuesta a los comentarios – atzz

0

Estaba obteniendo este error con zmq. La solución fue incluir el manifiesto python27.dll en el archivo libzmq.pyd (y probablemente funcionará para otros archivos pyd/dll). Asegúrese de utilizar todos los de 64 bits o todos los de 32 bits.

"C:\Program Files (x86)\Windows Kits\8.0\bin\x64\mt.exe" -inputresource:C:\windows\system32\python27.dll;#2 -outputresource:libzmq.pyd;#2 

Ver https://code.google.com/p/pyodbc/issues/detail?id=214

Cuestiones relacionadas