1 #!/bin/sh 2 # 3 # Copyright (c) 2013 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 #@ This script builds a Debian Wheezy sysroot for building Google Chrome. 8 #@ 9 #@ Generally this script is invoked as: 10 #@ sysroot-creator-debian.wheezy.sh <mode> <args>* 11 #@ Available modes are shown below. 12 #@ 13 #@ List of modes: 14 15 ###################################################################### 16 # Config 17 ###################################################################### 18 19 set -o nounset 20 set -o errexit 21 22 readonly SCRIPT_DIR=$(dirname $0) 23 24 # This is where the staging sysroot is. 25 readonly INSTALL_ROOT_AMD64=$(pwd)/debian_wheezy_amd64_staging 26 readonly INSTALL_ROOT_I386=$(pwd)/debian_wheezy_i386_staging 27 28 readonly REQUIRED_TOOLS="wget" 29 30 ###################################################################### 31 # Package Config 32 ###################################################################### 33 34 # this is where we get all the debian packages from 35 readonly DEBIAN_REPO=http://http.us.debian.org/debian 36 37 readonly PACKAGE_LIST_AMD64="${DEBIAN_REPO}/dists/wheezy/main/binary-amd64/Packages.bz2" 38 readonly PACKAGE_LIST_I386="${DEBIAN_REPO}/dists/wheezy/main/binary-i386/Packages.bz2" 39 40 # TODO(thestig) Remove unused libbz2 packages in the next sysroot update. 41 # Sysroot packages: these are the packages needed to build chrome. 42 # NOTE: When DEBIAN_PACKAGES is modified, the packagelist files must be updated 43 # by running this script in GeneratePackageList mode. 44 readonly DEBIAN_PACKAGES="\ 45 comerr-dev \ 46 gcc-4.6 \ 47 krb5-multidev \ 48 libasound2 \ 49 libasound2-dev \ 50 libatk1.0-0 \ 51 libatk1.0-dev \ 52 libavahi-client3 \ 53 libavahi-common3 \ 54 libbz2-1.0 \ 55 libbz2-dev \ 56 libc6 \ 57 libc6-dev \ 58 libcairo2 \ 59 libcairo2-dev \ 60 libcairo-gobject2 \ 61 libcairo-script-interpreter2 \ 62 libcomerr2 \ 63 libcups2 \ 64 libcups2-dev \ 65 libdbus-1-3 \ 66 libdbus-1-dev \ 67 libdbus-glib-1-2 \ 68 libelf1 \ 69 libelf-dev \ 70 libexpat1 \ 71 libexpat1-dev \ 72 libffi5 \ 73 libfontconfig1 \ 74 libfontconfig1-dev \ 75 libfreetype6 \ 76 libfreetype6-dev \ 77 libgcc1 \ 78 libgcc1 \ 79 libgconf-2-4 \ 80 libgconf2-4 \ 81 libgconf2-dev \ 82 libgcrypt11 \ 83 libgcrypt11-dev \ 84 libgdk-pixbuf2.0-0 \ 85 libgdk-pixbuf2.0-dev \ 86 libglib2.0-0 \ 87 libglib2.0-dev \ 88 libgnome-keyring0 \ 89 libgnome-keyring-dev \ 90 libgnutls26 \ 91 libgnutls-dev \ 92 libgnutls-openssl27 \ 93 libgnutlsxx27 \ 94 libgomp1 \ 95 libgpg-error0 \ 96 libgpg-error-dev \ 97 libgssapi-krb5-2 \ 98 libgssrpc4 \ 99 libgtk2.0-0 \ 100 libgtk2.0-dev \ 101 libk5crypto3 \ 102 libkadm5clnt-mit8 \ 103 libkadm5srv-mit8 \ 104 libkdb5-6 \ 105 libkeyutils1 \ 106 libkrb5-3 \ 107 libkrb5-dev \ 108 libkrb5support0 \ 109 libnspr4 \ 110 libnspr4-dev \ 111 libnss3 \ 112 libnss3-dev \ 113 libnss-db \ 114 liborbit2 \ 115 libp11-2 \ 116 libp11-kit0 \ 117 libpam0g \ 118 libpam0g-dev \ 119 libpango1.0-0 \ 120 libpango1.0-dev \ 121 libpci3 \ 122 libpci-dev \ 123 libpcre3 \ 124 libpcre3-dev \ 125 libpcrecpp0 \ 126 libpixman-1-0 \ 127 libpixman-1-dev \ 128 libpng12-0 \ 129 libpng12-dev \ 130 libpulse0 \ 131 libpulse-dev \ 132 libpulse-mainloop-glib0 \ 133 libquadmath0 \ 134 libselinux1 \ 135 libspeechd2 \ 136 libspeechd-dev \ 137 libssl1.0.0 \ 138 libssl-dev \ 139 libstdc++6 \ 140 libstdc++6-4.6-dev \ 141 libtasn1-3 \ 142 libudev0 \ 143 libudev-dev \ 144 libx11-6 \ 145 libx11-dev \ 146 libxau6 \ 147 libxau-dev \ 148 libxcb1 \ 149 libxcb1-dev \ 150 libxcb-render0 \ 151 libxcb-render0-dev \ 152 libxcb-shm0 \ 153 libxcb-shm0-dev \ 154 libxcomposite1 \ 155 libxcomposite-dev \ 156 libxcursor1 \ 157 libxcursor-dev \ 158 libxdamage1 \ 159 libxdamage-dev \ 160 libxdmcp6 \ 161 libxext6 \ 162 libxext-dev \ 163 libxfixes3 \ 164 libxfixes-dev \ 165 libxi6 \ 166 libxi-dev \ 167 libxinerama1 \ 168 libxinerama-dev \ 169 libxrandr2 \ 170 libxrandr-dev \ 171 libxrender1 \ 172 libxrender-dev \ 173 libxss1 \ 174 libxss-dev \ 175 libxt6 \ 176 libxt-dev \ 177 libxtst6 \ 178 libxtst-dev \ 179 linux-libc-dev \ 180 speech-dispatcher \ 181 x11proto-composite-dev \ 182 x11proto-core-dev \ 183 x11proto-damage-dev \ 184 x11proto-fixes-dev \ 185 x11proto-input-dev \ 186 x11proto-kb-dev \ 187 x11proto-randr-dev \ 188 x11proto-record-dev \ 189 x11proto-render-dev \ 190 x11proto-scrnsaver-dev \ 191 x11proto-xext-dev \ 192 zlib1g \ 193 zlib1g-dev" 194 195 readonly DEBIAN_DEP_LIST_AMD64="${SCRIPT_DIR}/packagelist.debian.wheezy.amd64" 196 readonly DEBIAN_DEP_LIST_I386="${SCRIPT_DIR}/packagelist.debian.wheezy.i386" 197 readonly DEBIAN_DEP_FILES_AMD64="$(cat ${DEBIAN_DEP_LIST_AMD64})" 198 readonly DEBIAN_DEP_FILES_I386="$(cat ${DEBIAN_DEP_LIST_I386})" 199 200 ###################################################################### 201 # Helper 202 ###################################################################### 203 204 Banner() { 205 echo "######################################################################" 206 echo $* 207 echo "######################################################################" 208 } 209 210 211 SubBanner() { 212 echo "......................................................................" 213 echo $* 214 echo "......................................................................" 215 } 216 217 218 Usage() { 219 egrep "^#@" "$0" | cut --bytes=3- 220 } 221 222 223 DownloadOrCopy() { 224 if [ -f "$2" ] ; then 225 echo "$2 already in place" 226 return 227 fi 228 229 HTTP=0 230 echo "$1" | grep -qs ^http:// && HTTP=1 231 if [ "$HTTP" = "1" ]; then 232 SubBanner "downloading from $1 -> $2" 233 wget "$1" -O "$2" 234 else 235 SubBanner "copying from $1" 236 cp "$1" "$2" 237 fi 238 } 239 240 241 SetEnvironmentVariables() { 242 ARCH="" 243 echo $1 | grep -qs Amd64$ && ARCH=AMD64 244 if [ -z "$ARCH" ]; then 245 echo $1 | grep -qs I386$ && ARCH=I386 246 fi 247 case "$ARCH" in 248 AMD64) 249 INSTALL_ROOT="$INSTALL_ROOT_AMD64"; 250 ;; 251 I386) 252 INSTALL_ROOT="$INSTALL_ROOT_I386"; 253 ;; 254 *) 255 echo "ERROR: Unexpected bad architecture." 256 exit 1 257 ;; 258 esac 259 } 260 261 Cleanup() { 262 rm -rf "$TMP" 263 } 264 265 # some sanity checks to make sure this script is run from the right place 266 # with the right tools 267 SanityCheck() { 268 Banner "Sanity Checks" 269 270 if [ "$(basename $(pwd))" != "sysroot_scripts" ] ; then 271 echo -n "ERROR: run this script from " 272 echo "src/chrome/installer/linux/sysroot_scripts" 273 exit 1 274 fi 275 276 if ! mkdir -p "${INSTALL_ROOT}" ; then 277 echo "ERROR: ${INSTALL_ROOT} can't be created." 278 exit 1 279 fi 280 281 TMP=$(mktemp -q -t -d debian-wheezy-XXXXXX) 282 if [ -z "$TMP" ]; then 283 echo "ERROR: temp dir can't be created." 284 exit 1 285 fi 286 trap Cleanup 0 287 288 for tool in ${REQUIRED_TOOLS} ; do 289 if ! which ${tool} ; then 290 echo "Required binary $tool not found." 291 echo "Exiting." 292 exit 1 293 fi 294 done 295 } 296 297 298 ChangeDirectory() { 299 # Change directory to where this script is. 300 cd $(dirname "$0") 301 } 302 303 304 ClearInstallDir() { 305 Banner "clearing dirs in ${INSTALL_ROOT}" 306 rm -rf ${INSTALL_ROOT}/* 307 } 308 309 310 CreateTarBall() { 311 local tarball=$1 312 Banner "creating tar ball ${tarball}" 313 tar zcf ${tarball} -C ${INSTALL_ROOT} . 314 } 315 316 ###################################################################### 317 # 318 ###################################################################### 319 320 HacksAndPatchesAmd64() { 321 Banner "Misc Hacks & Patches" 322 # these are linker scripts with absolute pathnames in them 323 # which we rewrite here 324 lscripts="${INSTALL_ROOT}/usr/lib/x86_64-linux-gnu/libpthread.so \ 325 ${INSTALL_ROOT}/usr/lib/x86_64-linux-gnu/libc.so" 326 327 #SubBanner "Rewriting Linker Scripts" 328 sed -i -e 's|/usr/lib/x86_64-linux-gnu/||g' ${lscripts} 329 sed -i -e 's|/lib/x86_64-linux-gnu/||g' ${lscripts} 330 331 # This is for chrome's ./build/linux/pkg-config-wrapper 332 # which overwrites PKG_CONFIG_PATH internally 333 SubBanner "Package Configs Symlink" 334 mkdir -p ${INSTALL_ROOT}/usr/share 335 ln -s ../lib/x86_64-linux-gnu/pkgconfig ${INSTALL_ROOT}/usr/share/pkgconfig 336 337 SubBanner "Adding an additional ld.conf include" 338 LD_SO_HACK_CONF="${INSTALL_ROOT}/etc/ld.so.conf.d/zz_hack.conf" 339 echo /usr/lib/gcc/x86_64-linux-gnu/4.6 > "$LD_SO_HACK_CONF" 340 echo /usr/lib >> "$LD_SO_HACK_CONF" 341 } 342 343 344 HacksAndPatchesI386() { 345 Banner "Misc Hacks & Patches" 346 # these are linker scripts with absolute pathnames in them 347 # which we rewrite here 348 lscripts="${INSTALL_ROOT}/usr/lib/i386-linux-gnu/libpthread.so \ 349 ${INSTALL_ROOT}/usr/lib/i386-linux-gnu/libc.so" 350 351 #SubBanner "Rewriting Linker Scripts" 352 sed -i -e 's|/usr/lib/i386-linux-gnu/||g' ${lscripts} 353 sed -i -e 's|/lib/i386-linux-gnu/||g' ${lscripts} 354 355 # This is for chrome's ./build/linux/pkg-config-wrapper 356 # which overwrites PKG_CONFIG_PATH internally 357 SubBanner "Package Configs Symlink" 358 mkdir -p ${INSTALL_ROOT}/usr/share 359 ln -s ../lib/i386-linux-gnu/pkgconfig ${INSTALL_ROOT}/usr/share/pkgconfig 360 361 SubBanner "Adding an additional ld.conf include" 362 LD_SO_HACK_CONF="${INSTALL_ROOT}/etc/ld.so.conf.d/zz_hack.conf" 363 echo /usr/lib/gcc/i486-linux-gnu/4.6 > "$LD_SO_HACK_CONF" 364 echo /usr/lib >> "$LD_SO_HACK_CONF" 365 } 366 367 368 InstallIntoSysroot() { 369 Banner "Install Libs And Headers Into Jail" 370 371 mkdir -p ${TMP}/debian-packages 372 mkdir -p ${INSTALL_ROOT} 373 for file in $@ ; do 374 local package="${TMP}/debian-packages/${file##*/}" 375 Banner "installing ${file}" 376 DownloadOrCopy ${DEBIAN_REPO}/pool/${file} ${package} 377 SubBanner "extracting to ${INSTALL_ROOT}" 378 if [ ! -s "${package}" ] ; then 379 echo 380 echo "ERROR: bad package ${package}" 381 exit 1 382 fi 383 dpkg --fsys-tarfile ${package}\ 384 | tar -xvf - --exclude=./usr/share -C ${INSTALL_ROOT} 385 done 386 } 387 388 389 CleanupJailSymlinks() { 390 Banner "jail symlink cleanup" 391 392 SAVEDPWD=$(pwd) 393 cd ${INSTALL_ROOT} 394 find lib lib64 usr/lib -type l -printf '%p %l\n' | while read link target; do 395 # skip links with non-absolute paths 396 echo "${target}" | grep -qs ^/ || continue 397 echo "${link}: ${target}" 398 case "${link}" in 399 usr/lib/gcc/x86_64-linux-gnu/4.*/* | usr/lib/gcc/i486-linux-gnu/4.*/*) 400 # Relativize the symlink. 401 ln -snfv "../../../../..${target}" "${link}" 402 ;; 403 usr/lib/x86_64-linux-gnu/* | usr/lib/i386-linux-gnu/*) 404 # Relativize the symlink. 405 ln -snfv "../../..${target}" "${link}" 406 ;; 407 usr/lib/*) 408 # Relativize the symlink. 409 ln -snfv "../..${target}" "${link}" 410 ;; 411 lib64/* | lib/*) 412 # Relativize the symlink. 413 ln -snfv "..${target}" "${link}" 414 ;; 415 esac 416 done 417 418 find lib lib64 usr/lib -type l -printf '%p %l\n' | while read link target; do 419 # Make sure we catch new bad links. 420 if [ ! -r "${link}" ]; then 421 echo "ERROR: FOUND BAD LINK ${link}" 422 ls -l ${link} 423 exit 1 424 fi 425 done 426 cd "$SAVEDPWD" 427 } 428 429 #@ 430 #@ BuildSysrootAmd64 <tarball-name> 431 #@ 432 #@ Build everything and package it 433 BuildSysrootAmd64() { 434 ClearInstallDir 435 InstallIntoSysroot ${DEBIAN_DEP_FILES_AMD64} 436 CleanupJailSymlinks 437 HacksAndPatchesAmd64 438 CreateTarBall $1 439 } 440 441 #@ 442 #@ BuildSysrootI386 <tarball-name> 443 #@ 444 #@ Build everything and package it 445 BuildSysrootI386() { 446 ClearInstallDir 447 InstallIntoSysroot ${DEBIAN_DEP_FILES_I386} 448 CleanupJailSymlinks 449 HacksAndPatchesI386 450 CreateTarBall $1 451 } 452 453 # 454 # GeneratePackageList 455 # 456 # Looks up package names in ${TMP}/Packages and write list of URLs 457 # to output file. 458 # 459 GeneratePackageList() { 460 local output_file=$1 461 echo "Updating: ${output_file}" 462 /bin/rm -f ${output_file} 463 shift 464 for pkg in $@ ; do 465 local pkg_full=$(grep -A 1 " ${pkg}\$" ${TMP}/Packages | egrep -o "pool/.*") 466 if [ -z "${pkg_full}" ]; then 467 echo "ERROR: missing package: $pkg" 468 exit 1 469 fi 470 echo $pkg_full | sed "s/^pool\///" >> $output_file 471 done 472 # sort -o does an in-place sort of this file 473 sort $output_file -o $output_file 474 } 475 476 #@ 477 #@ UpdatePackageListsAmd64 478 #@ 479 #@ Regenerate the package lists such that they contain an up-to-date 480 #@ list of URLs within the Debian archive. (For amd64) 481 UpdatePackageListsAmd64() { 482 local package_list="${TMP}/Packages.wheezy_amd64.bz2" 483 DownloadOrCopy ${PACKAGE_LIST_AMD64} ${package_list} 484 bzcat ${package_list} | egrep '^(Package:|Filename:)' > ${TMP}/Packages 485 486 GeneratePackageList ${DEBIAN_DEP_LIST_AMD64} "${DEBIAN_PACKAGES}" 487 } 488 489 #@ 490 #@ UpdatePackageListsI386 491 #@ 492 #@ Regenerate the package lists such that they contain an up-to-date 493 #@ list of URLs within the Debian archive. (For i386) 494 UpdatePackageListsI386() { 495 local package_list="${TMP}/Packages.wheezy_i386.bz2" 496 DownloadOrCopy ${PACKAGE_LIST_I386} ${package_list} 497 bzcat ${package_list} | egrep '^(Package:|Filename:)' > ${TMP}/Packages 498 499 GeneratePackageList ${DEBIAN_DEP_LIST_I386} "${DEBIAN_PACKAGES}" 500 } 501 502 if [ $# -eq 0 ] ; then 503 echo "ERROR: you must specify a mode on the commandline" 504 echo 505 Usage 506 exit 1 507 elif [ "$(type -t $1)" != "function" ]; then 508 echo "ERROR: unknown function '$1'." >&2 509 echo "For help, try:" 510 echo " $0 help" 511 exit 1 512 else 513 ChangeDirectory 514 SetEnvironmentVariables "$1" 515 SanityCheck 516 "$@" 517 fi 518