Windows: Fix build.bash again.
[icculus/xz.git] / windows / build.bash
1 #!/bin/bash
2 #
3 ###############################################################################
4 #
5 # Build a binary package on Windows with MinGW and MSYS
6 #
7 # Set the paths where MinGW, Mingw-w32, or MinGW-w64 are installed. If both
8 # MinGW and MinGW-w32 are specified, MinGW will be used. If there is no
9 # 32-bit or 64-bit compiler at all, it is simply skipped.
10 #
11 # Optionally, 7-Zip is used to create the final .zip and .7z packages.
12 # If you have installed it in the default directory, this script should
13 # find it automatically. Otherwise adjust the path manually.
14 #
15 # If you want to use a cross-compiler e.g. on GNU/Linux, this script won't
16 # work out of the box. You need to omit "make check" commands and replace
17 # u2d with some other tool to convert newlines from LF to CR+LF. You will
18 # also need to pass the --host option to configure.
19 #
20 ###############################################################################
21 #
22 # Author: Lasse Collin
23 #
24 # This file has been put into the public domain.
25 # You can do whatever you want with this file.
26 #
27 ###############################################################################
28
29 MINGW_DIR=/c/devel/tools/mingw
30 MINGW_W32_DIR=/c/devel/tools/mingw-w32
31 MINGW_W64_DIR=/c/devel/tools/mingw-w64
32
33 for SEVENZ_EXE in "$PROGRAMW6432/7-Zip/7z.exe" "$PROGRAMFILES/7-Zip/7z.exe" \
34                 "/c/Program Files/7-Zip/7z.exe"
35 do
36         [ -x "$SEVENZ_EXE" ] && break
37 done
38
39
40 # Abort immediately if something goes wrong.
41 set -e
42
43 # White spaces in directory names may break things so catch them immediately.
44 case $(pwd) in
45         ' ' | ' ' | '
46 ') echo "Error: White space in the directory name" >&2; exit 1 ;;
47 esac
48
49 # This script can be run either at the top-level directory of the package
50 # or in the same directory containing this script.
51 if [ ! -f windows/build.bash ]; then
52         cd ..
53         if [ ! -f windows/build.bash ]; then
54                 echo "You are in a wrong directory." >&2
55                 exit 1
56         fi
57 fi
58
59 # Run configure and copy the binaries to the given directory.
60 #
61 # The first argument is the directory where to copy the binaries.
62 # The rest of the arguments are passed to configure.
63 buildit()
64 {
65         DESTDIR=$1
66         BUILD=$2
67         CFLAGS=$3
68
69         # Clean up if it was already configured.
70         [ -f Makefile ] && make distclean
71
72         # Build the size-optimized binaries. Note that I don't want to
73         # provide size-optimized liblzma (shared nor static), because
74         # that isn't thread-safe now, and depending on bunch of things,
75         # maybe it will never be on Windows (pthreads-win32 helps but
76         # static liblzma might bit a bit tricky with it).
77         ./configure \
78                 --prefix= \
79                 --disable-nls \
80                 --disable-threads \
81                 --disable-shared \
82                 --enable-small \
83                 --build="$BUILD" \
84                 CFLAGS="$CFLAGS -Os"
85         make check
86
87         mkdir -pv "$DESTDIR"
88         cp -v src/xzdec/{xz,lzma}dec.exe src/lzmainfo/lzmainfo.exe "$DESTDIR"
89
90         make distclean
91
92         # Build the normal speed-optimized binaries. Note that while
93         # --disable-threads has been documented to make some things
94         # thread-unsafe, it's not actually true with this combination
95         # of configure flags in XZ Utils 5.0.x. Things can (and probably
96         # will) change after 5.0.x, and this script will be updated too.
97         ./configure \
98                 --prefix= \
99                 --disable-nls \
100                 --disable-threads \
101                 --build="$BUILD" \
102                 CFLAGS="$CFLAGS -O2"
103         make -C src/liblzma
104         make -C src/xz LDFLAGS=-static
105         make -C tests check
106
107         cp -v src/xz/xz.exe src/liblzma/.libs/liblzma.a "$DESTDIR"
108         cp -v src/liblzma/.libs/liblzma-*.dll "$DESTDIR/liblzma.dll"
109
110         strip -v "$DESTDIR/"*.{exe,dll}
111         strip -vg "$DESTDIR/"*.a
112 }
113
114 # Copy files and convert newlines from LF to CR+LF. Optinally add a suffix
115 # to the destination filename.
116 #
117 # The first argument is the destination directory. The second argument is
118 # the suffix to append to the filenames; use empty string if no extra suffix
119 # is wanted. The rest of the arguments are actual the filenames.
120 txtcp()
121 {
122         DESTDIR=$1
123         SUFFIX=$2
124         shift 2
125         for SRCFILE; do
126                 DESTFILE="$DESTDIR/${SRCFILE##*/}$SUFFIX"
127                 echo "Converting \`$SRCFILE' -> \`$DESTFILE'"
128                 u2d < "$SRCFILE" > "$DESTFILE"
129         done
130 }
131
132 # FIXME: Make sure that we don't get i686 or i586 code from the runtime.
133 # Actually i586 would be fine, but i686 probably not if the idea is to
134 # support even Win95.
135 #
136 # FIXME: Using i486 in the configure triplet may be wrong.
137 if [ -d "$MINGW_DIR" ]; then
138         # 32-bit x86, Win95 or later, using MinGW
139         PATH=$MINGW_DIR/bin:$PATH \
140                         buildit \
141                         pkg/bin_i486 \
142                         i486-pc-mingw32 \
143                         '-march=i486 -mtune=generic'
144 elif [ -d "$MINGW_W32_DIR" ]; then
145         # 32-bit x86, Win95 or later, using MinGW-w32
146         PATH=$MINGW_W32_DIR/bin:$MINGW_W32_DIR/i686-w64-mingw32/bin:$PATH \
147                         buildit \
148                         pkg/bin_i486 \
149                         i486-w64-mingw32 \
150                         '-march=i486 -mtune=generic'
151 fi
152
153 if [ -d "$MINGW_W64_DIR" ]; then
154         # 64-bit x86, WinXP or later, using MinGW-w64
155         PATH=$MINGW_W64_DIR/bin:$MINGW_W64_DIR/x86_64-w64-mingw32/bin:$PATH \
156                         buildit \
157                         pkg/bin_x86-64 \
158                         x86_64-w64-mingw32 \
159                         '-march=x86-64 -mtune=generic'
160 fi
161
162 # Copy the headers, the .def file, and the docs.
163 # They are the same for all architectures and builds.
164 mkdir -pv pkg/{include/lzma,doc/manuals}
165 txtcp pkg/include "" src/liblzma/api/lzma.h
166 txtcp pkg/include/lzma "" src/liblzma/api/lzma/*.h
167 txtcp pkg/doc "" src/liblzma/liblzma.def
168 txtcp pkg/doc .txt AUTHORS COPYING NEWS README THANKS TODO
169 txtcp pkg/doc "" doc/*.txt
170 txtcp pkg/doc/manuals "" doc/man/txt/{xz,xzdec,lzmainfo}.txt
171 cp -v doc/man/pdf-*/{xz,xzdec,lzmainfo}-*.pdf pkg/doc/manuals
172 txtcp pkg "" windows/README-Windows.txt
173
174 # Create the package. This requires 7z.exe from 7-Zip. If it wasn't found,
175 # this step is skipped and you have to zip it yourself.
176 VER=$(sh build-aux/version.sh)
177 cd pkg
178 if [ -x "$SEVENZ_EXE" ]; then
179         "$SEVENZ_EXE" a -tzip ../xz-$VER-windows.zip *
180         "$SEVENZ_EXE" a ../xz-$VER-windows.7z *
181 else
182         echo
183         echo "NOTE: 7z.exe was not found. xz-$VER-windows.zip"
184         echo "      and xz-$VER-windows.7z were not created."
185         echo "      You can create them yourself from the pkg directory."
186 fi
187
188 echo
189 echo "Build completed successfully."
190 echo