Difference between revisions of "Cross-Compiling Under Linux"

From WxWiki
Jump to navigation Jump to search
(Some notes for Debian folks)
Line 16: Line 16:
 
'''Note:''' The SDL scripts and these directions cannot be mixed.
 
'''Note:''' The SDL scripts and these directions cannot be mixed.
 
'''Note:''' By disabling threads (with --disable-threads), you can avoid a dependency on the ming dll
 
'''Note:''' By disabling threads (with --disable-threads), you can avoid a dependency on the ming dll
 +
 +
=== Some more details for Debian folks ===
 +
 +
After apt-getting the three packages mingw32, mingw32-binutils and mingw32-runtime from "unstable" as well as the wxWindows source (took the "2.6.2 all ports combined", but MSW should be enough), I found out that I had to set a lot of environment variables in order for configure to use the mingw32 executables:
 +
<pre>
 +
export CC=i586-mingw32msvc-gcc
 +
export CXX=i586-mingw32msvc-g++
 +
export LD=i586-mingw32msvc-ld
 +
export AR=i586-mingw32msvc-ar
 +
export AS=i586-mingw32msvc-as
 +
export NM=i586-mingw32msvc-nm
 +
export STRIP=i586-mingw32msvc-strip
 +
export RANLIB=i586-mingw32msvc-ranlib
 +
export DLLTOOL=i586-mingw32msvc-dlltool
 +
export OBJDUMP=i586-mingw32msvc-objdump
 +
export RESCOMP=i586-mingw32msvc-windres
 +
export CFLAGS=
 +
</pre>
 +
If you save that in a file, say, don't forget that you shouldn't ''execute'', but ''source'' it! Then
 +
<pre>
 +
./configure --prefix=/usr/local/i586-mingw32 --host=i586-mingw32msvc --target=i586-mingw32msvc \
 +
      --with-msw [--your_optional_switches]
 +
make
 +
make install</pre>
 +
(or <tt>sudo make install</tt>, depending what rights you have on <tt>/usr/local/i586-mingw32</tt>).
 +
 +
Your wxMSW libraries will be created in the directory you specified with <tt>--prefix</tt>, here it's <tt>/usr/local/i586-mingw32</tt>
  
 
== Example usage ==
 
== Example usage ==

Revision as of 17:44, 23 March 2006

Cross-compiling under Linux

  • Install The Mingw Cross-Compiler.
  • Compile wxWidgets
    • Download wxWidgets source
    • Compile with ./configure --prefix=/usr/local/i386-mingw32 --host=i386-mingw32 --target=i386-mingw32 --with-msw --your_optional_switches
    make
    make install

See also:

Note: The SDL scripts and these directions cannot be mixed. Note: By disabling threads (with --disable-threads), you can avoid a dependency on the ming dll

Some more details for Debian folks

After apt-getting the three packages mingw32, mingw32-binutils and mingw32-runtime from "unstable" as well as the wxWindows source (took the "2.6.2 all ports combined", but MSW should be enough), I found out that I had to set a lot of environment variables in order for configure to use the mingw32 executables:

export CC=i586-mingw32msvc-gcc
export CXX=i586-mingw32msvc-g++
export LD=i586-mingw32msvc-ld 
export AR=i586-mingw32msvc-ar
export AS=i586-mingw32msvc-as
export NM=i586-mingw32msvc-nm
export STRIP=i586-mingw32msvc-strip
export RANLIB=i586-mingw32msvc-ranlib
export DLLTOOL=i586-mingw32msvc-dlltool
export OBJDUMP=i586-mingw32msvc-objdump
export RESCOMP=i586-mingw32msvc-windres
export CFLAGS=

If you save that in a file, say, don't forget that you shouldn't execute, but source it! Then

./configure --prefix=/usr/local/i586-mingw32 --host=i586-mingw32msvc --target=i586-mingw32msvc \
       --with-msw [--your_optional_switches]
make
make install

(or sudo make install, depending what rights you have on /usr/local/i586-mingw32).

Your wxMSW libraries will be created in the directory you specified with --prefix, here it's /usr/local/i586-mingw32

Example usage

Once installed, save the following file as winhello.c (stolen from Installing and Using the MinGW Cross-Compiler on Mac OS X:

/*
 * Hello, World for Win32
 * gcc winhello.c -o winhello.exe
 */

#include &lt;windows.h&gt;
int main(int argc, char *argv[])
{
	MessageBox(NULL, "Hello, world!", "Hello, world!", MB_OK);
	return 0;
}

To build the example, execute the following command:

 $ i386-mingw32-gcc winhello.c -o winhello.exe

and run it for example with wine wine winhello.exe .

Contrib libraries

Couldn't compile the contrib directory with the wxMSW 2.4.2 sources, use the latest cvs.

Flags

You might need these flags when compiling:

-Wl,--subsystem,windows -mwindows -DWINVER=0x0400 -D__WIN95__ -D__GNUWIN32__ -DSTRICT -DHAVE_W32API_H -D__WXMSW__ -D__WINDOWS__

And these while linking:

-lregex -lpng -ljpeg -lzlib -ltiff -lstdc++ -lgcc -lodbc32 -lwsock32 -lwinspool -lwinmm -lshell32 -lcomctl32 -lctl3d32 -lodbc32 -ladvapi32 -lodbc32 -lwsock32 -lopengl32 -lglu32 -lole32 -loleaut32 -luuid

environment variables

In order to use the cross-compiler tools you need to replace the normal tools in makefiles. This is easier to do just exporting some environment variables before running configure/make:

  export CC=i586-mingw32msvc-gcc
  export CXX=i586-mingw32msvc-c++
  export LD=i586-mingw32msvc-ld
  export AR=i586-mingw32msvc-ar
  export AS=i586-mingw32msvc-as
  export NM=i586-mingw32msvc-nm
  export STRIP=i586-mingw32msvc-strip
  export RANLIB=i586-mingw32msvc-ranlib
  export DLLTOOL=i586-mingw32msvc-dlltool
  export OBJDUMP=i586-mingw32msvc-objdump
  export RESCOMP=i586-mingw32msvc-windres

SDL's Script

See also: BuildCVS.txt in the tar of the SDL scripts

http://www.libsdl.org/extras/win32/cross/ contains scripts that automate the compiler build process described above.

Download build-cross.sh, cross-configure.sh, and cross-make.sh.

Run the script build-cross.sh.

Download the CVS version wxAll and uncompress it.

Copy cross-configure.sh and cross-make.sh to the wxWidgets-2.5.2 directory.

Run cross-configure.sh and cross-make.sh and you should be done. :-)

Autoconf supports cross-compilation natively

If your cross-suite is i586-mingw32msvc-{gcc,g++,ld,...}, just do ../configure --with-msw --target=i586-mingw32msvc --host=i586-mingw32msvc --build=i386-linux and all necessary tools will be prefixed automatically.

ATTENTION: Turn off binfmt support before running configure (Debian: /etc/init.d/binfmt-support stop), which invokes wine for .exe files; otherwise configure will think it does NOT use a cross-compiler.

Autoconf/Automake unit testing suites

(maybe this section should go somewhere else?)

It is possible to autotest your code using wine (you are using unit tests, right?). This makes it very easy to script code under Unix to build multiple platforms, then test, without intervention. This section focusses on testing console-able objects.

First familiarise yourself with building test binaries with autoconf and automake. I recommend cppunit (for C++ systems). There's plentiful documentation on cppunit's website on integrating cppunit with Makefile.am. One show-stopping step is the ability to test msw binaries in the same way (make check) one tests unix binaries.

To take advantage of wine (running your tests automatically with wine), first make sure that wine may run headless. If you have access to a graphical terminal then this isn't important (if you're Ok with having wine spout gobbledygock to a window with every run). Make sure your test-directory Makefile.am's have all TESTS tokens suffixed with $(EXEEXT):

TESTS = TestFoo$(EXEEXT)

check_PROGRAMS = TestFoo

...and so on.

Next add a configure.ac (you have upgraded to using .ac instead of .in, right?) line manipulating the macro TESTS_ENVIRONMENT:

AC_SUBST([TESTS_ENVIRONMENT], [$WINE])

In this I assume that WINE has been set with AC_CHECK_PROGS or something (even `WINE = wine'). This will have all tests run in the following format:

$(TESTS_ENVIRONMENT) $${dir}$$tst

Where dir is the path and tst is the test name (remember that EXEEXT). That's it: wine will return the exit code of your running binary. You can also put a special shell or other token in there, but that exceeds the focus of this documentation. This assumed automake-1.9 and autoconf-2.57 but I'm fairly certain it works in earlier versions of both (uncertain about autoconf-2.13 style).