How to build a Linux->MinGW32 Cross-Compiler
for Qt
Download build-cross.sh:
http://home.comcast.net/~jay.snyder/QtMinGW/build-cross.sh
This script is a slightly modified/updated version of Ray Kelm's
build-cross.sh
Download MinGW/GCC Sources from www.mingw.org
I used GCC/G++ 3.4.5 and binutils 2.16.91, but you can uses others if
you modify the script.
Contents:
Build the Compiler
New qmakespec file
Building Applications
Troubleshooting
Acknowledgements
References
1. Build the Qt-DLL on MS Windows
How to build Qt on windows with MinGW gcc is described here. After building take the
complete QTDIR from your MS Windows box to your GNU/Linux box.
This has to be done once for each Qt-Release you want to work with.
The Rest of the time you stay on GNU/Linux.
In case you wonder why we do not build the Qt-DLL with the cross
compiler on Linux: You would have to apply substancial changes to the
Qt build system which IMO are not worth the effort.
Start with configure.exe should you be interested to achieve this :-)
2. Build the MinGW cross compiler
There are lots of sources that explain how to build a cross compiler.
Search for links at www.mingw.org
if you want to know more.
I'm using a build script (build-mingw-cross.sh) which is mostly
identical to the one supplied by Paul Millar last year (see script
header).
Download: build-cross.sh
Download the following sources from www.mingw.org/download.shtml:
binutils-2.16.91-20060119-1-src.tar.gz
gcc-core-3.4.5-20060117-1-src.tar.gz
gcc-g++-3.4.5-20060117-1-src.tar.gz
mingw-runtime-3.9.tar.gz
w32api-3.6.tar.gz
Please this files in a directory called "sources" under the
directory that build-cross.sh is in.
Do not extract them as that will be done by the build script. Of
course
you should use newer versions of those files if available.
Before you build your cross compiler have a look into the script and
adjust some variables. Check at least these:
- Set BUILD_ROOT to the path where the sources for your build
should
be copied to. The default for BUILD_ROOT is $HOME/src/mingw which
should be fine for most cases. Beware: per default this path is
completely removed before building.
- Set PREFIX to the directory where you wish the cross compiler to
be installed. The default is $HOME/mingw. Beware:
don't set this to /usr as that would most certainly interfere with your
installed native gcc (in case this isn't obvious ;).
- Adjust GCC, BINUTILS, W32API and RUNTIME to reflect the versions
of the mingw-sources you are using.
You may want to have a look at the configure options of gcc and adjust
them to your needs.
Now just type:
The compiler executables and tools are placed into PREFIX/bin and named
like they would on windows (omitting the .exe - they are GNU/Linux
executables) but with a prefix i686-mingw32- (e.g.
i686-mingw32-gcc).
This prefix can be adjusted in the buildscript by changing the variable
TARGET accordingly.
3. Produce a new Qt spec file for the cross compiler.
We have to adjust the regular win32-g++ spec file for use under
GNU/Linux and the cross compiler.
Download the TARed spec directory win32-x-g.tar and extract it into your
$QTDIR/mkspecs (the copied windows version).
The compiler exectuables and tools have a naming convention like
"i686-mingw32-gcc". I usually use symlinks like ~/bin/x-win32-gcc ->
PREFIX/bin/i586-mingw32-gcc.
If you choose to have another convention adjust the names of gcc, g++,
strip and ar etc. in the spec file. You may need to
edit qmake.conf to fit your installation
4. Install the Free Qt-X11-Linux-Distribution
This is neccessary because during build you need some linux
executables. You can not use the executables build for windows.
The minimum you need is moc, but you probably want qmake, Qt Designer
and uic as well. That's it. You need no linux source at all, i.e. no
devel package.
!! Make sure you install the same version as the one you just
build on windows !!
5. Building applications
To build one of those famous hello world applications (without Qt) just
type:
PREFIX/bin/i586-mingw32-g++ -o hello.exe hello.cpp
or if you follow my symlink convention:
x-win32-g++ -o hello.exe hello.cpp
I personally do not use qmake but if you prefer qmake to generate
your Makefiles you must use the qmake from the linux distribution.
Make sure:
- QTDIR is set to the folder containing the build windows
distribution
- The linux versions of moc, uic, qmake are available
- The mingw toolset (e.g. PREFIX/bin/i586-mingw32-gcc) is available
- Add no_mocdepend to the config variable of your *.pro files
Let's take aclock from the Qt example folder as example:
Here is the adjusted aclock.pro:
##---start ----------------------------------------------------
TEMPLATE = app
CONFIG += qt warn_on release no_mocdepend
HEADERS = aclock.h
SOURCES = aclock.cpp \
main.cpp
TARGET = aclock
OBJECTS_DIR = tmp/obj
MOC_DIR = tmp/moc
##---end ------------------------------------------------------
Build the makefile with:
qmake -spec $QTDIR/mkspecs/win32-x-g++ aclock.pro -o Makefile
Build the aclock.exe with:
make
Troubleshooting:
I ran into a problem trying to use my Qt dll that was compiled
under windows with the mingw32-gcc cross compiler on Linux.
The problem was that the build of mingw32-gcc
resulting from build-cross.sh and the binaries for the win32 hosted
mingw are configured differently. If you get
unresolved externals for ___gxx_personality_sj0 or
___gxx_personality_v0, then the option _GLIBCXX_SJLJ_EXCEPTIONS is set
differently for the two builds.
The win32 hosted binary of the C++ standard library
had the symbol ___gxx_personality_sj0 in it, which ment that
sjlj-exceptions was turned on. The build
resulting from build-cross.sh had that options turned off, resulting in
the symbol ___gxx_personality_v0.
I had to add:
--enable-sjlj-exceptions
to the function configure_gcc() in build-cross.sh.
Once I did this, then all was well.
Acknowledgements:
I'd like to thank Heiko Gerdau ( see tchnosis link below for email) for
providing the initial information for this.
References:
http://www.technosis.de/mingw/crosscompile/
http://lists.trolltech.com/qt-interest/2006-03/thread00351-0.html
http://www.mingw.org/MinGWiki/index.php/build