4db53cb98b3dd8fa25bac913eef8a387efc4b617
[platform/framework/web/crosswalk.git] / src / chrome / tools / test / reference_build / chrome_linux / installer / debian / build.sh
1 #!/bin/bash
2 #
3 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
4 # Use of this source code is governed by a BSD-style license that can be
5 # found in the LICENSE file.
6
7 # TODO(mmoss) This currently only works with official builds, since non-official
8 # builds don't add the "${BUILDDIR}/installer/" files needed for packaging.
9
10 set -e
11 if [ "$VERBOSE" ]; then
12   set -x
13 fi
14 set -u
15
16 # Create the Debian changelog file needed by dpkg-gencontrol. This just adds a
17 # placeholder change, indicating it is the result of an automatic build.
18 # TODO(mmoss) Release packages should create something meaningful for a
19 # changelog, but simply grabbing the actual 'svn log' is way too verbose. Do we
20 # have any type of "significant/visible changes" log that we could use for this?
21 gen_changelog() {
22   rm -f "${DEB_CHANGELOG}"
23   process_template "${SCRIPTDIR}/changelog.template" "${DEB_CHANGELOG}"
24   debchange -a --nomultimaint -m --changelog "${DEB_CHANGELOG}" \
25     "Release Notes: ${RELEASENOTES}"
26   GZLOG="${STAGEDIR}/usr/share/doc/${PACKAGE}-${CHANNEL}/changelog.gz"
27   mkdir -p "$(dirname "${GZLOG}")"
28   gzip -9 -c "${DEB_CHANGELOG}" > "${GZLOG}"
29   chmod 644 "${GZLOG}"
30 }
31
32 # Create the Debian control file needed by dpkg-deb.
33 gen_control() {
34   dpkg-gencontrol -v"${VERSIONFULL}" -c"${DEB_CONTROL}" -l"${DEB_CHANGELOG}" \
35   -f"${DEB_FILES}" -p"${PACKAGE}-${CHANNEL}" -P"${STAGEDIR}" \
36   -O > "${STAGEDIR}/DEBIAN/control"
37   rm -f "${DEB_CONTROL}"
38 }
39
40 # Setup the installation directory hierachy in the package staging area.
41 prep_staging_debian() {
42   prep_staging_common
43   install -m 755 -d "${STAGEDIR}/DEBIAN" \
44     "${STAGEDIR}/etc/cron.daily" \
45     "${STAGEDIR}/usr/share/menu" \
46     "${STAGEDIR}/usr/share/doc/${PACKAGE}"
47 }
48
49 # Put the package contents in the staging area.
50 stage_install_debian() {
51   # Always use a different name for /usr/bin symlink depending on channel.
52   # First, to avoid file collisions. Second, to make it possible to
53   # use update-alternatives for /usr/bin/google-chrome.
54   local USR_BIN_SYMLINK_NAME="${PACKAGE}-${CHANNEL}"
55
56   if [ "$CHANNEL" != "stable" ]; then
57     # This would ideally be compiled into the app, but that's a bit too
58     # intrusive of a change for these limited use channels, so we'll just hack
59     # it into the wrapper script. The user can still override since it seems to
60     # work to specify --user-data-dir multiple times on the command line, with
61     # the last occurrence winning.
62     local SXS_USER_DATA_DIR="\${XDG_CONFIG_HOME:-\${HOME}/.config}/${PACKAGE}-${CHANNEL}"
63     local DEFAULT_FLAGS="--user-data-dir=\"${SXS_USER_DATA_DIR}\""
64
65     # Avoid file collisions between channels.
66     local INSTALLDIR="${INSTALLDIR}-${CHANNEL}"
67
68     # TODO(phajdan.jr): Do that for all packages for SxS,
69     # http://crbug.com/38598 .
70     if [ "$CHANNEL" = "trunk" ] || [ "$CHANNEL" = "asan" ]; then
71       local PACKAGE="${PACKAGE}-${CHANNEL}"
72     fi
73
74     # Make it possible to distinguish between menu entries
75     # for different channels.
76     local MENUNAME="${MENUNAME} (${CHANNEL})"
77   fi
78   prep_staging_debian
79   stage_install_common
80   echo "Staging Debian install files in '${STAGEDIR}'..."
81   install -m 755 -d "${STAGEDIR}/${INSTALLDIR}/cron"
82   process_template "${BUILDDIR}/installer/common/repo.cron" \
83       "${STAGEDIR}/${INSTALLDIR}/cron/${PACKAGE}"
84   chmod 755 "${STAGEDIR}/${INSTALLDIR}/cron/${PACKAGE}"
85   pushd "${STAGEDIR}/etc/cron.daily/"
86   ln -snf "${INSTALLDIR}/cron/${PACKAGE}" "${PACKAGE}"
87   popd
88   process_template "${BUILDDIR}/installer/debian/debian.menu" \
89     "${STAGEDIR}/usr/share/menu/${PACKAGE}.menu"
90   chmod 644 "${STAGEDIR}/usr/share/menu/${PACKAGE}.menu"
91   process_template "${BUILDDIR}/installer/debian/postinst" \
92     "${STAGEDIR}/DEBIAN/postinst"
93   chmod 755 "${STAGEDIR}/DEBIAN/postinst"
94   process_template "${BUILDDIR}/installer/debian/prerm" \
95     "${STAGEDIR}/DEBIAN/prerm"
96   chmod 755 "${STAGEDIR}/DEBIAN/prerm"
97   process_template "${BUILDDIR}/installer/debian/postrm" \
98     "${STAGEDIR}/DEBIAN/postrm"
99   chmod 755 "${STAGEDIR}/DEBIAN/postrm"
100 }
101
102 # Actually generate the package file.
103 do_package() {
104   echo "Packaging ${ARCHITECTURE}..."
105   PREDEPENDS="$COMMON_PREDEPS"
106   DEPENDS="${COMMON_DEPS}"
107   # Trunk is a special package, mostly for development testing, so don't make
108   # it replace any installed release packages.
109   if [ "$CHANNEL" != "trunk" ] && [ "$CHANNEL" != "asan" ]; then
110     REPLACES="${PACKAGE}"
111     CONFLICTS="${PACKAGE}"
112     PROVIDES="${PACKAGE}, www-browser"
113   fi
114   gen_changelog
115   process_template "${SCRIPTDIR}/control.template" "${DEB_CONTROL}"
116   export DEB_HOST_ARCH="${ARCHITECTURE}"
117   if [ -f "${DEB_CONTROL}" ]; then
118     gen_control
119   fi
120   fakeroot dpkg-deb -Zlzma -b "${STAGEDIR}" .
121 }
122
123 # Remove temporary files and unwanted packaging output.
124 cleanup() {
125   echo "Cleaning..."
126   rm -rf "${STAGEDIR}"
127   rm -rf "${TMPFILEDIR}"
128 }
129
130 usage() {
131   echo "usage: $(basename $0) [-c channel] [-a target_arch] [-o 'dir'] "
132   echo "                      [-b 'dir']"
133   echo "-c channel the package channel (trunk, asan, unstable, beta, stable)"
134   echo "-a arch    package architecture (ia32 or x64)"
135   echo "-o dir     package output directory [${OUTPUTDIR}]"
136   echo "-b dir     build input directory    [${BUILDDIR}]"
137   echo "-h         this help message"
138 }
139
140 # Check that the channel name is one of the allowable ones.
141 verify_channel() {
142   case $CHANNEL in
143     stable )
144       CHANNEL=stable
145       RELEASENOTES="http://googlechromereleases.blogspot.com/search/label/Stable%20updates"
146       ;;
147     unstable|dev|alpha )
148       CHANNEL=unstable
149       RELEASENOTES="http://googlechromereleases.blogspot.com/search/label/Dev%20updates"
150       ;;
151     testing|beta )
152       CHANNEL=beta
153       RELEASENOTES="http://googlechromereleases.blogspot.com/search/label/Beta%20updates"
154       ;;
155     trunk|asan )
156       # Setting this to empty will prevent it from updating any existing configs
157       # from release packages.
158       REPOCONFIG=""
159       RELEASENOTES="http://googlechromereleases.blogspot.com/"
160       ;;
161     * )
162       echo
163       echo "ERROR: '$CHANNEL' is not a valid channel type."
164       echo
165       exit 1
166       ;;
167   esac
168 }
169
170 process_opts() {
171   while getopts ":o:b:c:a:h" OPTNAME
172   do
173     case $OPTNAME in
174       o )
175         OUTPUTDIR=$(readlink -f "${OPTARG}")
176         mkdir -p "${OUTPUTDIR}"
177         ;;
178       b )
179         BUILDDIR=$(readlink -f "${OPTARG}")
180         ;;
181       c )
182         CHANNEL="$OPTARG"
183         ;;
184       a )
185         TARGETARCH="$OPTARG"
186         ;;
187       h )
188         usage
189         exit 0
190         ;;
191       \: )
192         echo "'-$OPTARG' needs an argument."
193         usage
194         exit 1
195         ;;
196       * )
197         echo "invalid command-line option: $OPTARG"
198         usage
199         exit 1
200         ;;
201     esac
202   done
203 }
204
205 #=========
206 # MAIN
207 #=========
208
209 SCRIPTDIR=$(readlink -f "$(dirname "$0")")
210 OUTPUTDIR="${PWD}"
211 STAGEDIR=$(mktemp -d -t deb.build.XXXXXX) || exit 1
212 TMPFILEDIR=$(mktemp -d -t deb.tmp.XXXXXX) || exit 1
213 DEB_CHANGELOG="${TMPFILEDIR}/changelog"
214 DEB_FILES="${TMPFILEDIR}/files"
215 DEB_CONTROL="${TMPFILEDIR}/control"
216 CHANNEL="trunk"
217 # Default target architecture to same as build host.
218 if [ "$(uname -m)" = "x86_64" ]; then
219   TARGETARCH="x64"
220 else
221   TARGETARCH="ia32"
222 fi
223
224 # call cleanup() on exit
225 trap cleanup 0
226 process_opts "$@"
227 if [ ! "$BUILDDIR" ]; then
228   BUILDDIR=$(readlink -f "${SCRIPTDIR}/../../../../../out/Release")
229 fi
230
231 source ${BUILDDIR}/installer/common/installer.include
232
233 get_version_info
234 VERSIONFULL="${VERSION}-${PACKAGE_RELEASE}"
235
236 if [ "$CHROMIUM_BUILD" = "_google_chrome" ]; then
237   source "${BUILDDIR}/installer/common/google-chrome.info"
238 else
239   source "${BUILDDIR}/installer/common/chromium-browser.info"
240 fi
241 eval $(sed -e "s/^\([^=]\+\)=\(.*\)$/export \1='\2'/" \
242   "${BUILDDIR}/installer/theme/BRANDING")
243
244 REPOCONFIG="deb http://dl.google.com/linux/chrome/deb/ stable main"
245 verify_channel
246
247 # Some Debian packaging tools want these set.
248 export DEBFULLNAME="${MAINTNAME}"
249 export DEBEMAIL="${MAINTMAIL}"
250
251 # We'd like to eliminate more of these deps by relying on the 'lsb' package, but
252 # that brings in tons of unnecessary stuff, like an mta and rpm. Until that full
253 # 'lsb' package is installed by default on DEB distros, we'll have to stick with
254 # the LSB sub-packages, to avoid pulling in all that stuff that's not installed
255 # by default.
256
257 # Need a dummy debian/control file for dpkg-shlibdeps.
258 DUMMY_STAGING_DIR="${TMPFILEDIR}/dummy_staging"
259 mkdir "$DUMMY_STAGING_DIR"
260 cd "$DUMMY_STAGING_DIR"
261 mkdir debian
262 touch debian/control
263
264 # Generate the dependencies,
265 # TODO(mmoss): This is a workaround for a problem where dpkg-shlibdeps was
266 # resolving deps using some of our build output shlibs (i.e.
267 # out/Release/lib.target/libfreetype.so.6), and was then failing with:
268 #   dpkg-shlibdeps: error: no dependency information found for ...
269 # It's not clear if we ever want to look in LD_LIBRARY_PATH to resolve deps,
270 # but it seems that we don't currently, so this is the most expediant fix.
271 SAVE_LDLP=${LD_LIBRARY_PATH:-}
272 unset LD_LIBRARY_PATH
273 DPKG_SHLIB_DEPS=$(dpkg-shlibdeps -O "$BUILDDIR/chrome" 2> /dev/null | \
274   sed 's/^shlibs:Depends=//')
275 if [ -n "$SAVE_LDLP" ]; then
276   LD_LIBRARY_PATH=$SAVE_LDLP
277 fi
278
279 # Format it nicely and save it for comparison.
280 # The grep -v is for a duplicate libc6 dep caused by Lucid glibc silliness.
281 echo "$DPKG_SHLIB_DEPS" | sed 's/, /\n/g' | \
282   grep -v '^libc6 (>= 2.3.6-6~)$' > actual
283
284 # Compare the expected dependency list to the generate list.
285 BAD_DIFF=0
286 diff "$SCRIPTDIR/expected_deps" actual || BAD_DIFF=1
287 if [ $BAD_DIFF -ne 0 ] && [ -z "${IGNORE_DEPS_CHANGES:-}" ]; then
288   echo
289   echo "ERROR: Shared library dependencies changed!"
290   echo "If this is intentional, please update:"
291   echo "chrome/installer/linux/debian/expected_deps"
292   echo
293   exit $BAD_DIFF
294 fi
295 rm -rf "$DUMMY_STAGING_DIR"
296
297 # Additional dependencies not in the dpkg-shlibdeps output.
298 # Pull a more recent version of NSS than required by runtime linking, for
299 # security and stability updates in NSS.
300 ADDITION_DEPS="ca-certificates, libcurl3, libnss3 (>= 3.14.3), \
301   lsb-base (>=3.2), xdg-utils (>= 1.0.2), wget"
302
303 # Fix-up libnspr dependency due to renaming in Ubuntu (the old package still
304 # exists, but it was moved to "universe" repository, which isn't installed by
305 # default).
306 DPKG_SHLIB_DEPS=$(sed \
307     's/\(libnspr4-0d ([^)]*)\), /\1 | libnspr4 (>= 4.9.5-0ubuntu0), /g' \
308     <<< $DPKG_SHLIB_DEPS)
309
310 # Fix-up libudev dependency because Ubuntu 13.04 has libudev1 instead of
311 # libudev0.
312 DPKG_SHLIB_DEPS=$(sed 's/\(libudev0 ([^)]*)\), /\1 | libudev1 (>= 198), /g' \
313                   <<< $DPKG_SHLIB_DEPS)
314
315 COMMON_DEPS="${DPKG_SHLIB_DEPS}, ${ADDITION_DEPS}"
316 COMMON_PREDEPS="dpkg (>= 1.14.0)"
317
318
319 # Make everything happen in the OUTPUTDIR.
320 cd "${OUTPUTDIR}"
321
322 case "$TARGETARCH" in
323   ia32 )
324     export ARCHITECTURE="i386"
325     stage_install_debian
326     ;;
327   x64 )
328     export ARCHITECTURE="amd64"
329     stage_install_debian
330     ;;
331   * )
332     echo
333     echo "ERROR: Don't know how to build DEBs for '$TARGETARCH'."
334     echo
335     exit 1
336     ;;
337 esac
338
339 do_package