Difference between revisions of "Cross-Compile"

From UFO:AI
Jump to navigation Jump to search
Line 3: Line 3:
 
In this article we will cross-compile UFO:AI in a Debian chroot environment to Windows, using MingW64_64 (64bit).
 
In this article we will cross-compile UFO:AI in a Debian chroot environment to Windows, using MingW64_64 (64bit).
  
I chose a chroot environment, as it kind of standardizing the build environment and fairly cheap to build. You can achieve the same in Docker or other containerization techniques, but chroot just does its job.
+
We chose a chroot environment, as it kind of standardizing the build environment and fairly cheap to build. You can achieve the same in Docker or other containerization techniques, but chroot just does its job.
  
  
Line 33: Line 33:
 
  mycomputer ~ # mount --bind /sys /ufoai.xcompile/sys
 
  mycomputer ~ # mount --bind /sys /ufoai.xcompile/sys
  
If you plan to keep this environment permanent you can also move these mountings to `/etc/fstab`.
+
If you plan to keep this environment permanent you can also move these mountings to `/etc/fstab` of your host machine.
  
  
It is a good idea to make it clear when we're in the chroot environment via the prompt:
+
It is a good idea to make it clear when you're in the chroot environment via the prompt:
  
 
  mycomputer ~ # echo "export PS1='\\u@chroot:\\w \\\$ '" >> /ufoai.xcompile/root/.bashrc
 
  mycomputer ~ # echo "export PS1='\\u@chroot:\\w \\\$ '" >> /ufoai.xcompile/root/.bashrc
Line 44: Line 44:
 
=== Enter ===
 
=== Enter ===
  
 +
Entering chroot is just a command:
 
  mycomputer ~ # chroot /ufoai.xcompile
 
  mycomputer ~ # chroot /ufoai.xcompile
 
  root@chroot:/ #
 
  root@chroot:/ #
  
  
= Preparing the build environment =
+
= Dependencies and build tools =
  
Update the package manager and any obsolete packages:
+
To make step easier, we built a Bash (v4.0+) script {{path|contrib/scripts/cross-env.sh}} to prepare the chroot for building UFO:AI.
root@chroot:/ # apt-get update && apt-get update
+
It installs the mingw cross-compiler and other tools, downloads necessary libraries and compiles them.
  
 +
root@chroot:/development/ufoai.git # contrib/scripts/cross-env.sh
  
root@chroot:/ # apt-get install \
+
''Please note that the script currently misses requirements of the UFORadiant map editor.''
    git \
+
''Some optional dependencies are also missed, like video playing support and backtraces''
    libz-mingw-w64-dev \
 
    make \
 
    mingw-w64 \
 
    python3 \
 
    wget \
 
    zip
 
  
  
Create a directory
+
= Cross-Compiling UFO:AI =
root@chroot:/ mkdir /development
 
root@chroot:/ export DEVEL_DIR=/development
 
root@chroot:/ cd "$DEVEL_DIR"
 
root@chroot:/development #
 
  
 +
Check out the source code if you haven't done yet [Getting_the_source]. Enter the directory and run configure.
  
== Dependencies ==
+
root@chroot:/development/ufoai.git # ./configure --target-os=mingw64_64
 +
...
 +
Build modules:
 +
Build cgame-campaign
 +
Build cgame-multiplayer
 +
Build cgame-skirmish
 +
Build game
 +
Build testall
 +
Build ufo
 +
Build ufo2map
 +
Build ufoded
 +
Build ufomodel
 +
Disable uforadiant
 +
- Gtk2 missing - GtkGL missing
  
We've installed the compiler, build tools and `zlib` using the package manager, however we need to compile other dependencies for Windows with MinGW also.
+
Consider adding configure options as needed:
 +
* --enable-release
 +
* --prefix
 +
* --datadir
 +
* --libdir
 +
* --localedir
 +
* --bindir
  
=== Download dependencies ===
+
''Read more on command-line options in the configure script's help.''
 +
root@chroot:/development/ufoai.git # ./configure --help
  
Always use the latest compatible version of the dependencies as they can contain important fixes to bugs, including security vulnerabilities.
+
To compile the game, run its make target.
 +
root@chroot:/development/ufoai.git # make -j 4 ufo
  
* cURL: {{https|curl.se/windows/dl-8.9.1_1/curl-8.9.1_1-win64-mingw.zip}}
+
The Unit-test suite '''testall''' is a bit special, as it requires '''ufo2map''' and its ''test maps'' to be compiled. However in a Linux cross-compile environment, you cannot run '''ufo2map.exe''' ''(without help, like wine)''. If you just want to compile the test suite, a workaround is compiling '''ufo2map.exe''', then creating empty files for the compiled maps, then compiling the test suite. The order matters as '''make''' check file timestamps for dependency resolution.
* Iconv: {{https|ftp.gnu.org/pub/gnu/libiconv/libiconv-1.17.tar.gz}}
+
root@chroot:/development/ufoai.git # make -j 4 ufo2map
* Intl: {{https|ftp.gnu.org/pub/gnu/gettext/gettext-0.22.5.tar.gz}}
+
root@chroot:/development/ufoai.git # touch unittest/maps/test_game.bsp
* Jpeg: {{https|github.com/libjpeg-turbo/libjpeg-turbo/archive/refs/tags/3.0.3.tar.gz}}
+
root@chroot:/development/ufoai.git # touch unittest/maps/test_reverse_door.bsp
* Lua 5.4: {{https|www.lua.org/ftp/lua-5.4.7.tar.gz}}
+
root@chroot:/development/ufoai.git # touch unittest/maps/test_routing.bsp
* OGG: {{https|downloads.xiph.org/releases/ogg/libogg-1.3.5.tar.gz}}
+
root@chroot:/development/ufoai.git # make -j 4 testall
* PNG: {{https|sourceforge.net/projects/libpng/files/libpng16/1.6.43/libpng-1.6.43.tar.gz/download}}
 
* SDL2: {{https|github.com/libsdl-org/SDL_mixer/releases/download/release-2.8.0/SDL2_mixer-devel-2.8.0-mingw.tar.gz}}
 
** ''SDL3'' is about to be released, but it probably won't be a simple drop-in replacement. For now we need SDL2.
 
* SDL2-Mixer: {{https|github.com/libsdl-org/SDL_mixer/releases/download/release-2.8.0/SDL2_mixer-devel-2.8.0-mingw.tar.gz}}
 
* SDL2-TTF: {{https|github.com/libsdl-org/SDL_ttf/releases/download/release-2.22.0/SDL2_ttf-devel-2.22.0-mingw.tar.gz}}
 
* Vorbis: {{https|downloads.xiph.org/releases/vorbis/libvorbis-1.3.7.tar.gz}}
 
  
  
 +
As mentioned before UFORadiant needs more work, as it needs the whole Gtk2+ eco-system.
  
  
 +
== needed DLLs ==
  
''(to be continued)''
+
To run the game we need to pack the dynamically linked DLLs into the game. My tests suggested these are:
 +
* base/game.dll (of course, the battlescape engine)
 +
* libcurl-x64.dll
 +
* libgcc_s_seh-1.dll
 +
* libiconv-2.dll
 +
* libintl-8.dll
 +
* libjpeg-62.dll
 +
* libstdc++-6.dll
 +
* libwinpthread-1.dll
 +
* SDL2.dll
 +
* SDL2_mixer.dll
 +
* SDL2_ttf.dll
 +
* zlib1.dll

Revision as of 22:45, 19 August 2024

Cross-Compile from Linux to Windows

In this article we will cross-compile UFO:AI in a Debian chroot environment to Windows, using MingW64_64 (64bit).

We chose a chroot environment, as it kind of standardizing the build environment and fairly cheap to build. You can achieve the same in Docker or other containerization techniques, but chroot just does its job.


Building the chroot

Prerequisites

For this step you will need:

  1. Debootstrap: Debootstrap is a program that can fetch and construct a Debian-like filesystem. This is the only software you need to install on your system. It is available on all major distributions, if you are unsure, check it on Repology.
  2. Root access: You will need to be able to run commands as system administrator (`su` or `sudo`).
  3. Disk space: You will need around 7-10GiB free space for the cross-compilation.
  4. Internet access: You will need to download packages and libraries from the Internet.


Build

As root user, create a directory and call `debootstrap` to build the root filesystem into that. We are using /ufoai.xcompile in this example, but use any path you like!

mycomputer ~ # mkdir /ufoai.xcompile
mycomputer ~ # debootstrap stable /ufoai.xcompile
...

Mount the pseudo-filesystems:

mycomputer ~ # mount --bind /dev /ufoai.xcompile/dev
mycomputer ~ # mount --bind /dev/pts /ufoai.xcompile/dev/pts
mycomputer ~ # mount --bind /proc /ufoai.xcompile/proc
mycomputer ~ # mount --bind /sys /ufoai.xcompile/sys

If you plan to keep this environment permanent you can also move these mountings to `/etc/fstab` of your host machine.


It is a good idea to make it clear when you're in the chroot environment via the prompt:

mycomputer ~ # echo "export PS1='\\u@chroot:\\w \\\$ '" >> /ufoai.xcompile/root/.bashrc
mycomputer ~ # echo "export PS1='\\u@chroot:\\w \\\$ '" >> /ufoai.xcompile/etc/skel/.bashrc


Enter

Entering chroot is just a command:

mycomputer ~ # chroot /ufoai.xcompile
root@chroot:/ #


Dependencies and build tools

To make step easier, we built a Bash (v4.0+) script contrib/scripts/cross-env.sh to prepare the chroot for building UFO:AI. It installs the mingw cross-compiler and other tools, downloads necessary libraries and compiles them.

root@chroot:/development/ufoai.git # contrib/scripts/cross-env.sh

Please note that the script currently misses requirements of the UFORadiant map editor. Some optional dependencies are also missed, like video playing support and backtraces


Cross-Compiling UFO:AI

Check out the source code if you haven't done yet [Getting_the_source]. Enter the directory and run configure.

root@chroot:/development/ufoai.git # ./configure --target-os=mingw64_64
...
Build modules:
Build cgame-campaign
Build cgame-multiplayer
Build cgame-skirmish
Build game
Build testall
Build ufo
Build ufo2map
Build ufoded
Build ufomodel
Disable uforadiant
- Gtk2 missing	- GtkGL missing

Consider adding configure options as needed:

  • --enable-release
  • --prefix
  • --datadir
  • --libdir
  • --localedir
  • --bindir

Read more on command-line options in the configure script's help.

root@chroot:/development/ufoai.git # ./configure --help

To compile the game, run its make target.

root@chroot:/development/ufoai.git # make -j 4 ufo

The Unit-test suite testall is a bit special, as it requires ufo2map and its test maps to be compiled. However in a Linux cross-compile environment, you cannot run ufo2map.exe (without help, like wine). If you just want to compile the test suite, a workaround is compiling ufo2map.exe, then creating empty files for the compiled maps, then compiling the test suite. The order matters as make check file timestamps for dependency resolution.

root@chroot:/development/ufoai.git # make -j 4 ufo2map
root@chroot:/development/ufoai.git # touch unittest/maps/test_game.bsp
root@chroot:/development/ufoai.git # touch unittest/maps/test_reverse_door.bsp
root@chroot:/development/ufoai.git # touch unittest/maps/test_routing.bsp
root@chroot:/development/ufoai.git # make -j 4 testall


As mentioned before UFORadiant needs more work, as it needs the whole Gtk2+ eco-system.


needed DLLs

To run the game we need to pack the dynamically linked DLLs into the game. My tests suggested these are:

  • base/game.dll (of course, the battlescape engine)
  • libcurl-x64.dll
  • libgcc_s_seh-1.dll
  • libiconv-2.dll
  • libintl-8.dll
  • libjpeg-62.dll
  • libstdc++-6.dll
  • libwinpthread-1.dll
  • SDL2.dll
  • SDL2_mixer.dll
  • SDL2_ttf.dll
  • zlib1.dll