domingo, 13 de marzo de 2016

ZinjaI en Windows: ¿Qué compilador elegir?

Existen muchos ports a Windows de GCC y de las demás herramientas/bibliotecas afines. En ZinjaI siempre usé MinGW. En su momento, hace unos años, era la opción por defecto casi sin pensarlo, pero la situación ha cambiado. Para empezar, MinGW ha quedado atado por definición a los 32 bits, mientras que la mayoría de las PCs modernas y sus sistemas operativos son de 64. Para seguir, el ritmo de actualización de MinGW se ha ralentizado bastante, o al menos eso parece en comparación con la velocidad a la que han avanzado las demás versiones. El problema es que las alternativas son muchas, hay nuevas decisiones que hacer para elegir una, y desde mi punto de vista no emerge una opción claramente ganadora de todo esto.

Mantener uno de estos no es tarea fácil. No se trata de simplemente tomar los fuentes de GCC que usamos en GNU/Linux y compilarlos en Windows. Hay cientos de parches que aplicar, hay que agregar y mantener cabeceras y bibliotecas adicionales (como la WinAPI), hay que lidiar con problemas inesperados como el de "no hay disco en la unidad", etc.

La versión de MinGW que uso en ZinjaI, que fue la "estable" por más de dos años y hasta hace unos 10 días, tiene desde errores "tontos" y molestos como no tener definidas las funciones "to_string" de C++11, hasta errores mucho menos evidentes que a veces hacen imposible la tarea de compilar bibliotecas como Qt o wxWidgets. Yo mismo tuve que aplicar algunos parches a los headers, y recompilar GDB para evitar problemas particularmente molestos en ZinjaI.

Hay otros MinGWs alternativos dando vueltas por Internet. Primero está MinGW64, que nace como un fork del MinGW original, pero llevado a 64 bits. Ya les comenté en algún momento cómo probarlo en ZinjaI. Lo bueno es que este último se ha mantenido mucho más activo y actualizado que su predecesor. Lo malo es para cada versión hay varias versiones. Pongamos por ejemplo una versión de GCC, digamos la 5.3 que es la última estable disponible. Hay compilaciones de GCC 5.3 en MinGW64 que usan hilos posix para dar soporte a los std::threads, y otras que se limitan a la winapi y no dan soporte completo. Y dentro de cada una hay dos sabores para elegir, denominados sjlj y dwarf, que varían en cuestiones finas relacionadas al manejo de excepciones.

Cualquiera de estas elecciones nos ata a una ABI con la que deberemos compilar también las bibliotecas que usemos, ya que no deberíamos mezclar partes compiladas con distintos "sabores" de MinGW64. Entonces, tengo que elegir con cuidado y luego mantenerme con esa decisión para no tener que obligar al usuario a reinstalar todos sus complementos con cada actualización (y yo tampoco quiero tener que recompilarlos a cada rato). Pero además hay otras disitribuciones de GCC para Windows. Entre las más populares puedo mencionar tdm-gcc y la del genial Mr. STL conocida como nuwen.

Y todavía no introducimos en el abanico de posibilidades a LLVM+Clang. Este conjunto es mucho más moderno, pero su uso en Windows todavía es más complicado. Por ejemplo: Clang no trae su propia biblioteca estándar, sino que debe usar la de MinGW o la de Visual Studio. La última vez que probé había que hardcodear en los fuentes de Clang la versión de MinGW a utilizar con sus paths, y recompilarlo para que la encontrara. Además, clang tiene menos miramientos a la hora de cortar la backward-compatibility. En la última versión, por ejemplo, deprecaron el soporte para Windows XP. XP sigue teniendo una cuota de mercado no despreciable, y en el contexto de las instituciones educativas diría que es lamentablemente mayor. No es todavía una opción para ZinjaI entonces pasar a un compilador que implique estas restricciones.

En resumen, hay mucho para elegir, y no es algo que sea fácil de cambiar como para probar uno a la ligera y ver que pasa. Lo que probablemente haga sea lo siguiente: empezar a ofrecer dos versiones de ZinjaI para Windows, una de 32 bits con el MinGW clásico y una nueva de 64. En la de 32 todo seguirá como siempre por un buen tiempo. Para la de 64, seguramente elija MinGW64 (aunque no se cual "sabor") y tendré que recompilar todos los complementos. Más aún, las versiones de 64bits también pueden generar binarios para 32bits, así que si quiero dar soporte a eso tengo que incluir dos compilaciones de cada biblioteca en cada complemento. Veremos de a poco cómo sale el cambio y, si todo va bien, a la larga la versión más utilizada pasará a ser la de 64.

1 comentario: