| OLD | NEW |
| 1 #!/bin/bash -e | 1 #!/bin/bash -e |
| 2 | 2 |
| 3 # Copyright (c) 2010 The Chromium Authors. All rights reserved. | 3 # Copyright (c) 2010 The Chromium Authors. All rights reserved. |
| 4 # Use of this source code is governed by a BSD-style license that can be | 4 # Use of this source code is governed by a BSD-style license that can be |
| 5 # found in the LICENSE file. | 5 # found in the LICENSE file. |
| 6 | 6 |
| 7 # This script installs Debian-derived distributions in a chroot environment. | 7 # This script installs Debian-derived distributions in a chroot environment. |
| 8 # It can for example be used to have an accurate 32bit build and test | 8 # It can for example be used to have an accurate 32bit build and test |
| 9 # environment when otherwise working on a 64bit machine. | 9 # environment when otherwise working on a 64bit machine. |
| 10 # N. B. it is unlikely that this script will ever work on anything other than a | 10 # N. B. it is unlikely that this script will ever work on anything other than a |
| 11 # Debian-derived system. | 11 # Debian-derived system. |
| 12 | 12 |
| 13 usage() { |
| 14 echo "usage: ${0##*/} [-m mirror]" |
| 15 echo "-m mirror an alternate repository mirror for package downloads" |
| 16 echo "-h this help message" |
| 17 } |
| 18 |
| 19 process_opts() { |
| 20 local OPTNAME OPTIND OPTERR OPTARG |
| 21 while getopts ":m:h" OPTNAME; do |
| 22 case "$OPTNAME" in |
| 23 m) |
| 24 if [ -n "${mirror}" ]; then |
| 25 echo "You can only specify exactly one mirror location" |
| 26 usage |
| 27 exit 1 |
| 28 fi |
| 29 mirror="$OPTARG" |
| 30 ;; |
| 31 h) |
| 32 usage |
| 33 exit 0 |
| 34 ;; |
| 35 \:) |
| 36 echo "'-$OPTARG' needs an argument." |
| 37 usage |
| 38 exit 1 |
| 39 ;; |
| 40 *) |
| 41 echo "invalid command-line option: $OPTARG" |
| 42 usage |
| 43 exit 1 |
| 44 ;; |
| 45 esac |
| 46 done |
| 47 |
| 48 if [ $# -ge ${OPTIND} ]; then |
| 49 eval echo "Unexpected command line argument: \${${OPTIND}}" |
| 50 usage |
| 51 exit 1 |
| 52 fi |
| 53 } |
| 54 |
| 55 |
| 13 # Check that we are running as a regular user | 56 # Check that we are running as a regular user |
| 14 [ "$(id -nu)" = root ] && { | 57 [ "$(id -nu)" = root ] && { |
| 15 echo "Run this script as a regular user and provide your \"sudo\"" \ | 58 echo "Run this script as a regular user and provide your \"sudo\"" \ |
| 16 "password if requested" >&2 | 59 "password if requested" >&2 |
| 17 exit 1 | 60 exit 1 |
| 18 } | 61 } |
| 19 mkdir -p "$HOME/chroot/" | 62 mkdir -p "$HOME/chroot/" |
| 20 | 63 |
| 64 process_opts "$@" |
| 65 |
| 21 # Error handler | 66 # Error handler |
| 22 trap 'exit 1' INT TERM QUIT | 67 trap 'exit 1' INT TERM QUIT |
| 23 trap 'sudo apt-get clean; tput bel; echo; echo Failed' EXIT | 68 trap 'sudo apt-get clean; tput bel; echo; echo Failed' EXIT |
| 24 | 69 |
| 25 # Install any missing applications that this script relies on. If these packages | 70 # Install any missing applications that this script relies on. If these packages |
| 26 # are already installed, don't force another "apt-get install". That would | 71 # are already installed, don't force another "apt-get install". That would |
| 27 # prevent them from being auto-removed, if they ever become eligible for that. | 72 # prevent them from being auto-removed, if they ever become eligible for that. |
| 28 # And as this script only needs the packages once, there is no good reason to | 73 # And as this script only needs the packages once, there is no good reason to |
| 29 # introduce a hard dependency on things such as dchroot and debootstrap. | 74 # introduce a hard dependency on things such as dchroot and debootstrap. |
| 30 dep= | 75 dep= |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 74 target="${distname}${arch}" | 119 target="${distname}${arch}" |
| 75 | 120 |
| 76 # Don't overwrite an existing installation | 121 # Don't overwrite an existing installation |
| 77 [ -d /var/lib/chroot/"${target}" ] && { | 122 [ -d /var/lib/chroot/"${target}" ] && { |
| 78 echo "This chroot already exists on your machine." >&2 | 123 echo "This chroot already exists on your machine." >&2 |
| 79 echo "Delete /var/lib/chroot/${target} if you want to start over." >&2 | 124 echo "Delete /var/lib/chroot/${target} if you want to start over." >&2 |
| 80 exit 1 | 125 exit 1 |
| 81 } | 126 } |
| 82 sudo mkdir -p /var/lib/chroot/"${target}" | 127 sudo mkdir -p /var/lib/chroot/"${target}" |
| 83 | 128 |
| 129 # Offer to include additional standard repositories for Ubuntu-based chroots. |
| 130 alt_repos= |
| 131 grep ubuntu.com /usr/share/debootstrap/scripts/"${distname}" >&/dev/null && { |
| 132 while :; do |
| 133 echo "Would you like to add ${distname}-updates and ${distname}-security " |
| 134 echo -n "to the chroot's sources.list (y/n)? " |
| 135 read alt_repos |
| 136 case "${alt_repos}" in |
| 137 y|Y) |
| 138 alt_repos="y" |
| 139 break |
| 140 ;; |
| 141 n|N) |
| 142 break |
| 143 ;; |
| 144 esac |
| 145 done |
| 146 } |
| 147 |
| 84 # Remove stale entry from /etc/schroot/schroot.conf. Entries start | 148 # Remove stale entry from /etc/schroot/schroot.conf. Entries start |
| 85 # with the target name in square brackets, followed by an arbitrary | 149 # with the target name in square brackets, followed by an arbitrary |
| 86 # number of lines. The entry stops when either the end of file has | 150 # number of lines. The entry stops when either the end of file has |
| 87 # been reached, or when the beginning of a new target is encountered. | 151 # been reached, or when the beginning of a new target is encountered. |
| 88 # This means, we cannot easily match for a range of lines in | 152 # This means, we cannot easily match for a range of lines in |
| 89 # "sed". Instead, we actually have to iterate over each line and check | 153 # "sed". Instead, we actually have to iterate over each line and check |
| 90 # whether it is the beginning of a new entry. | 154 # whether it is the beginning of a new entry. |
| 91 sudo sed -ni '/^[[]'"${target%bit}"']$/,${:1;n;/^[[]/b2;b1;:2;p;n;b2};p' \ | 155 sudo sed -ni '/^[[]'"${target%bit}"']$/,${:1;n;/^[[]/b2;b1;:2;p;n;b2};p' \ |
| 92 /etc/schroot/schroot.conf | 156 /etc/schroot/schroot.conf |
| 93 | 157 |
| 94 # Download base system. This takes some time | 158 # Download base system. This takes some time |
| 95 grep ubuntu.com /usr/share/debootstrap/scripts/"${distname}" >&/dev/null && | 159 if [ -z "${mirror}" ]; then |
| 96 mirror="http://archive.ubuntu.com/ubuntu" || | 160 grep ubuntu.com /usr/share/debootstrap/scripts/"${distname}" >&/dev/null && |
| 97 mirror="http://ftp.us.debian.org/debian" | 161 mirror="http://archive.ubuntu.com/ubuntu" || |
| 162 mirror="http://ftp.us.debian.org/debian" |
| 163 fi |
| 98 sudo debootstrap ${archflag} "${distname}" /var/lib/chroot/"${target}" \ | 164 sudo debootstrap ${archflag} "${distname}" /var/lib/chroot/"${target}" \ |
| 99 "$mirror" | 165 "$mirror" |
| 100 | 166 |
| 101 # Add new entry to /etc/schroot/schroot.conf | 167 # Add new entry to /etc/schroot/schroot.conf |
| 102 grep ubuntu.com /usr/share/debootstrap/scripts/"${distname}" >&/dev/null && | 168 grep ubuntu.com /usr/share/debootstrap/scripts/"${distname}" >&/dev/null && |
| 103 brand="Ubuntu" || brand="Debian" | 169 brand="Ubuntu" || brand="Debian" |
| 104 sudo sh -c 'cat >>/etc/schroot/schroot.conf' <<EOF | 170 sudo sh -c 'cat >>/etc/schroot/schroot.conf' <<EOF |
| 105 [${target%bit}] | 171 [${target%bit}] |
| 106 description=${brand} ${distname} ${arch} | 172 description=${brand} ${distname} ${arch} |
| 107 type=directory | 173 type=directory |
| (...skipping 24 matching lines...) Expand all Loading... |
| 132 exec schroot -c ${target%bit} -p | 198 exec schroot -c ${target%bit} -p |
| 133 else | 199 else |
| 134 p="\$1"; shift | 200 p="\$1"; shift |
| 135 exec schroot -c ${target%bit} -p "\$p" -- "\$@" | 201 exec schroot -c ${target%bit} -p "\$p" -- "\$@" |
| 136 fi | 202 fi |
| 137 exit 1 | 203 exit 1 |
| 138 EOF | 204 EOF |
| 139 sudo chown root:root /usr/local/bin/"${target%bit}" | 205 sudo chown root:root /usr/local/bin/"${target%bit}" |
| 140 sudo chmod 755 /usr/local/bin/"${target%bit}" | 206 sudo chmod 755 /usr/local/bin/"${target%bit}" |
| 141 | 207 |
| 208 # Add the standard Ubuntu update repositories if requested. |
| 209 [ "${alt_repos}" = "y" -a -r "/var/lib/chroot/${target}/etc/apt/sources.list" ]
&& |
| 210 sudo sed -i '/^deb .* [^ -]\+ main$/p |
| 211 s/^\(deb .* [^ -]\+\) main/\1-security main/ |
| 212 p |
| 213 t1 |
| 214 d |
| 215 :1;s/-security main/-updates main/ |
| 216 t |
| 217 d' "/var/lib/chroot/${target}/etc/apt/sources.list" |
| 218 |
| 142 # Add a few more repositories to the chroot | 219 # Add a few more repositories to the chroot |
| 143 [ -r /var/lib/chroot/${target}/etc/apt/sources.list ] && | 220 [ -r "/var/lib/chroot/${target}/etc/apt/sources.list" ] && |
| 144 sudo sed -i 's/ main$/ main restricted universe multiverse/ | 221 sudo sed -i 's/ main$/ main restricted universe multiverse/ |
| 145 p | 222 p |
| 146 t1 | 223 t1 |
| 147 d | 224 d |
| 148 :1;s/^deb/deb-src/ | 225 :1;s/^deb/deb-src/ |
| 149 t | 226 t |
| 150 d' /var/lib/chroot/${target}/etc/apt/sources.list | 227 d' "/var/lib/chroot/${target}/etc/apt/sources.list" |
| 151 | 228 |
| 152 # Update packages | 229 # Update packages |
| 153 sudo schroot -c "${target%bit}" -p -- /bin/sh -c ' | 230 sudo schroot -c "${target%bit}" -p -- /bin/sh -c ' |
| 154 apt-get update; apt-get -y dist-upgrade' || : | 231 apt-get update; apt-get -y dist-upgrade' || : |
| 155 | 232 |
| 156 # Install a couple of missing packages | 233 # Install a couple of missing packages |
| 157 for i in debian-keyring ubuntu-keyring locales sudo; do | 234 for i in debian-keyring ubuntu-keyring locales sudo; do |
| 158 [ -d "/var/lib/chroot/${target}/usr/share/doc/$i" ] || | 235 [ -d "/var/lib/chroot/${target}/usr/share/doc/$i" ] || |
| 159 sudo schroot -c "${target%bit}" -p -- apt-get -y install "$i" || : | 236 sudo schroot -c "${target%bit}" -p -- apt-get -y install "$i" || : |
| 160 done | 237 done |
| (...skipping 18 matching lines...) Expand all Loading... |
| 179 # If running a 32bit environment on a 64bit machine, install a few binaries | 256 # If running a 32bit environment on a 64bit machine, install a few binaries |
| 180 # as 64bit. | 257 # as 64bit. |
| 181 if [ "${arch}" = 32bit ] && file /bin/bash 2>/dev/null | grep -q x86-64; then | 258 if [ "${arch}" = 32bit ] && file /bin/bash 2>/dev/null | grep -q x86-64; then |
| 182 sudo schroot -c "${target%bit}" -p -- apt-get -y install \ | 259 sudo schroot -c "${target%bit}" -p -- apt-get -y install \ |
| 183 lib64expat1 lib64ncurses5 lib64readline6 lib64z1 | 260 lib64expat1 lib64ncurses5 lib64readline6 lib64z1 |
| 184 dep= | 261 dep= |
| 185 for i in binutils gdb strace; do | 262 for i in binutils gdb strace; do |
| 186 [ -d /usr/share/doc/"$i" ] || dep="$dep $i" | 263 [ -d /usr/share/doc/"$i" ] || dep="$dep $i" |
| 187 done | 264 done |
| 188 [ -n "$dep" ] && sudo apt-get -y install $dep | 265 [ -n "$dep" ] && sudo apt-get -y install $dep |
| 189 sudo cp /usr/bin/gdb /var/lib/chroot/${target}/usr/local/bin/ | 266 sudo cp /usr/bin/gdb "/var/lib/chroot/${target}/usr/local/bin/" |
| 190 sudo cp /usr/bin/ld /var/lib/chroot/${target}/usr/local/bin/ | 267 sudo cp /usr/bin/ld "/var/lib/chroot/${target}/usr/local/bin/" |
| 191 for i in libbfd libpython; do | 268 for i in libbfd libpython; do |
| 192 lib="$({ ldd /usr/bin/ld; ldd /usr/bin/gdb; } | | 269 lib="$({ ldd /usr/bin/ld; ldd /usr/bin/gdb; } | |
| 193 grep "$i" | awk '{ print $3 }')" | 270 grep "$i" | awk '{ print $3 }')" |
| 194 if [ -n "$lib" -a -r "$lib" ]; then | 271 if [ -n "$lib" -a -r "$lib" ]; then |
| 195 sudo cp "$lib" /var/lib/chroot/${target}/usr/lib64/ | 272 sudo cp "$lib" "/var/lib/chroot/${target}/usr/lib64/" |
| 196 fi | 273 fi |
| 197 done | 274 done |
| 198 for lib in libssl libcrypt; do | 275 for lib in libssl libcrypt; do |
| 199 sudo cp /usr/lib/$lib* /var/lib/chroot/${target}/usr/lib64/ || : | 276 sudo cp /usr/lib/$lib* "/var/lib/chroot/${target}/usr/lib64/" || : |
| 200 done | 277 done |
| 201 fi | 278 fi |
| 202 | 279 |
| 203 # Clean up package files | 280 # Clean up package files |
| 204 sudo schroot -c "${target%bit}" -p -- apt-get clean | 281 sudo schroot -c "${target%bit}" -p -- apt-get clean |
| 205 sudo apt-get clean | 282 sudo apt-get clean |
| 206 | 283 |
| 207 # Let the user know what we did | 284 # Let the user know what we did |
| 208 trap '' INT TERM QUIT | 285 trap '' INT TERM QUIT |
| 209 trap '' EXIT | 286 trap '' EXIT |
| 210 cat <<EOF | 287 cat <<EOF |
| 211 | 288 |
| 212 | 289 |
| 213 Successfully installed ${distname} ${arch} | 290 Successfully installed ${distname} ${arch} |
| 214 | 291 |
| 215 You can run programs inside of the chroot by invoking the "${target%bit}" | 292 You can run programs inside of the chroot by invoking the "${target%bit}" |
| 216 command. | 293 command. |
| 217 | 294 |
| 218 Your home directory is shared between the host and the chroot. But I configured | 295 Your home directory is shared between the host and the chroot. But I configured |
| 219 $HOME/chroot to be private to the chroot environment. You can use it | 296 $HOME/chroot to be private to the chroot environment. You can use it |
| 220 for files that need to differ between environments. | 297 for files that need to differ between environments. |
| 221 EOF | 298 EOF |
| OLD | NEW |