On Mon, May 26, 2008 at 10:43:44PM +0200, Sylvain Beucler wrote: > Hi, > > I'm tring to cross-compile Guile from GNU/Linux with mingw (so I can > statically build guile in a .exe without having to use that other OS). > > I cross-compiled gmp and libltdl (dependencies). > Now I have a few troubles with guile: > > > Act I) Configuration > > $ CPPFLAGS="-I/usr/local/cross-tools/i386-mingw32msvc/include" \ > LDFLAGS="-L/usr/local/cross-tools/i386-mingw32msvc/lib" \ > ./configure --host=i586-mingw32msvc --build=i686-pc-linux-gnu > [...] > checking for restartable system calls... configure: error: cannot run test > program while cross compiling > > The problem apparently lies in configure.in, macro AC_SYS_RESTARTABLE_SYSCALLS > > Note that the autoconf documentation deprecates this macro: > "These days portable programs [...] should not rely on > `HAVE_RESTARTABLE_SYSCALLS', since nowadays whether a system call is > restartable is a dynamic issue, not a configuration-time issue." > > I commented it out for a start. > > > Act II) Compilation > > $ make > [...] > DLL_EXPORT -DPIC -o .libs/libguile_la-stime.o > cc1: warnings being treated as errors > stime.c:85: warning: ‘tzname’ redeclared without dllimport attribute: > previous dllimport ignored > > I found 2 references to this issue: > - http://cygwin.com/ml/cygwin/2008-01/msg00491.html > => removed tzname > - http://www.nabble.com/getdate-on-mingw:-tzname-problems-td14855896.html > => use HAVE_DECL_TZNAME instead > > I used the 2nd option: > # if !HAVE_DECL_TZNAME /* For SGI. */ > extern char *tzname[]; /* RS6000 and others reject char **tzname. */ > #endif > #if defined (__MINGW32__) > # define tzname _tzname > #endif > > > Act III) Linking > > i586-mingw32msvc-gcc -I/usr/local/cross-tools/i386-mingw32msvc/include -g -O2 > -Wall -Wmissing-prototypes -Werror .libs/guile.exeS.o > -I/usr/local/cross-tools/i386-mingw32msvc/include -o guile.exe guile-guile.o > -Wl,--export-dynamic -L/usr/local/cross-tools/i386-mingw32msvc/lib > ./.libs/libguile.a /usr/local/cross-tools/i386-mingw32msvc/lib/libgmp.a > -lws2_32 /usr/local/cross-tools/i386-mingw32msvc/lib/libltdl.dll.a > -L/usr/local/cross-tools/i386-mingw32msvc/lib > -L/usr/local/cross-tools/i386-mingw32msvc/lib > guile-guile.o: In function `main': > /usr/src/guile-1.8.5/libguile/guile.c:74: undefined reference to > `__imp__scm_boot_guile' > guile-guile.o: In function `inner_main': > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_options' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_language' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_result' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_output' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_output_length' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_maybe_valid_type_p' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_read' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_eval' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_print' > /usr/src/guile-1.8.5/libguile/guile.c:55: undefined reference to > `__imp__gdb_binding' > /usr/src/guile-1.8.5/libguile/guile.c:59: undefined reference to > `__imp__scm_shell' > collect2: ld returned 1 exit status > rm -f .libs/guile.exeS.o > make[3]: *** [guile.exe] Erreur 1 > > Duh! > I'm out of ideas. Help? :)
This one is apparently due to guile.c: #ifdef __MINGW32__ # define SCM_IMPORT 1 #endif When the error occured, the build system was apparently using libguile.la statically. In this case, __declspec (dllimport) need not be used, and so SCM_IMPORT need not be defined, so the linker won't use the '__imp__' symbols. ( The goat book uses a slightly more complex technique to detect the use of DLL imports: http://sources.redhat.com/autobook/autobook/autobook_255.html # ---------------------------------------------------------------------- # Win32 objects need to tell the header whether they will be linking # with a dll or static archive in order that everything is imported # to the object in the same way that it was exported from the # archive (extern for static, __declspec(dllimport) for dlls) # ---------------------------------------------------------------------- LIBHELLO_DLL_IMPORT= case "$host" in *-*-cygwin* | *-*-mingw* ) if test X"$enable_shared" = Xyes; then AC_TRY_LINK_FUNC([libhello_is_dll], [LIBHELLO_DLL_IMPORT=-DLIBHELLO_DLL_IMPORT]) fi ;; esac AC_SUBST(LIBHELLO_DLL_IMPORT) and then: #ifdef _WIN32 # ifdef DLL_EXPORT # define HELLO_SCOPE __declspec(dllexport) # else # ifdef LIBHELLO_DLL_IMPORT # define HELLO_SCOPE extern __declspec(dllimport) # endif # endif #endif #ifndef HELLO_SCOPE # define HELLO_SCOPE extern #endif ) With the ./configure line I mentioned, I then ran in to problems linking with gmp. GMP can't be built statically and as a DLL at once ("gmp.h is different for each", it says), so it was only built statically in my environment, and thus guile didn't link. So I added "--disable-shared" to ./configure, added an '#undefine SCM_IMPORT' in guile.c, and it eventually (cross-)compiled entirely. Now, how to properly fix it? :) -- Sylvain