Delete febootstrap-updates cache (viliar.net.ru).
[febootstrap.git] / febootstrap.sh
index 6700a9b..67687e5 100755 (executable)
 #
 # Written by Richard W.M. Jones <rjones@redhat.com>
 
+unset CDPATH
+
 TEMP=`getopt \
-        -o g:i: \
-        --long groupinstall:,group-install:,help,install: \
+        -o g:i:p:u: \
+        --long groupinstall:,group-install:,help,install:,noclean,no-clean,proxy:,updates: \
         -n febootstrap -- "$@"`
 if [ $? != 0 ]; then
     echo "febootstrap: problem parsing the command line arguments"
@@ -32,6 +34,8 @@ declare -a packages
 packages[0]="@Core"
 i=0
 
+clean=yes
+
 usage ()
 {
     echo "Usage: febootstrap [--options] REPO TARGET [MIRROR]"
@@ -43,9 +47,18 @@ while true; do
        -i|--install)
            packages[i++]="$2"
            shift 2;;
-       --groupinstall|--group-install)
+       -g|--groupinstall|--group-install)
            packages[i++]="@$2"
            shift 2;;
+       -p|--proxy)
+           proxy="proxy=$2"
+           shift 2;;
+       -u|--updates)
+           updates="$2";
+           shift 2;;
+       --noclean|--no-clean)
+           clean=no
+           shift;;
        --help)
            usage
            exit 0;;
@@ -69,7 +82,10 @@ mirror="$3"
 
 # Architecture is currently always the same as the current arch.  We
 # cannot do --foreign builds.  See discussion in the manpage.
-arch=$(arch)
+arch=$(uname -m)
+case $arch in
+    i?86) arch=i386 ;;
+esac
 
 # Create a temporary directory, make sure it gets cleaned up at the end.
 tmpdir=$(mktemp -d)
@@ -88,6 +104,7 @@ name=febootstrap $repo $arch
 failovermethod=priority
 enabled=1
 gpgcheck=0
+$proxy
 __EOF__
 
 # "Mirror" parameter is a bit misnamed, but it means a local mirror,
@@ -98,29 +115,132 @@ else
     echo "mirrorlist=http://mirrors.fedoraproject.org/mirrorlist?repo=$repo&arch=$arch" >> "$tmpdir"/febootstrap.repo
 fi
 
+# Add the updates repository if asked.
+case "$updates" in
+    ""|none|no)
+       ;;
+    *://*)
+       cat >> $tmpdir/febootstrap.repo <<EOF
+
+[febootstrap-updates]
+name=febootstrap updates $arch
+failovermethod=priority
+enabled=1
+gpgcheck=0
+$proxy
+baseurl=$updates
+EOF
+addrepo=febootstrap-updates
+       ;;
+    *)
+       cat >> $tmpdir/febootstrap.repo <<EOF
+
+[febootstrap-updates]
+name=febootstrap $updates $arch
+failovermethod=priority
+enabled=1
+gpgcheck=0
+$proxy
+mirrorlist=http://mirrors.fedoraproject.org/mirrorlist?repo=$updates&arch=$arch
+EOF
+addrepo=febootstrap-updates
+       ;;
+esac
+
 # Create the target filesystem.
 rm -rf "$target"
 mkdir "$target"
 
+# Target must be an absolute path.
+target=$(cd "$target" > /dev/null; pwd)
+
 # This is necessary to keep yum happy.  It's not clear why yum can't
 # just create this file itself.
 mkdir -p "$target"/var/cache/yum/febootstrap/packages
 
-yumargs="-y --disablerepo=* --enablerepo=febootstrap --noplugins --nogpgcheck"
+# NB: REQUIRED for useradd/groupadd to run properly.
+#
+# However this causes 'filesystem' RPM install to give the
+# following error.  Not sure how serious the error is:
+# error: unpacking of archive failed on file /proc: cpio: utime
+export FAKECHROOT_EXCLUDE_PATH=/proc
 
-# If we are root, then we don't need to run fakeroot and fakechroot.
-if [ $(id -u) -eq 0 ]; then
-    yum \
-        -c "$tmpdir"/febootstrap.repo \
-       $yumargs \
-       --installroot="$target" \
-       install "${packages[@]}"
-else
+# Substitute some statically-linked commands.  This is only supported
+# in fakechroot > 2.9.  For previous versions of fakechroot it is
+# ignored.
+export FAKECHROOT_CMD_SUBST=/sbin/ldconfig=/bin/true:/usr/sbin/glibc_post_upgrade.i686=/bin/true:/usr/sbin/glibc_post_upgrade.x86_64=/bin/true:/usr/sbin/build-locale-archive=/bin/true:/usr/sbin/libgcc_post_upgrade=/bin/true
+
+# Use the libraries inside the chroot.
+export LD_LIBRARY_PATH="$target"/usr/lib64:"$target"/usr/lib:"$target"/lib64:"$target"/usr/lib
+
+# Make the device nodes inside the fake chroot.
+# (Copied from mock/backend.py)  Why isn't there a base package which
+# creates these?
+make_device_nodes ()
+{
+    mkdir "$target"/proc
+    mkdir "$target"/sys
+    mkdir "$target"/dev
+    (
+       cd "$target"/dev
+       mkdir pts
+       mkdir shm
+       mkdir mapper
+       mknod null c 1 3;    chmod 0666 null
+       mknod full c 1 7;    chmod 0666 full
+       mknod zero c 1 5;    chmod 0666 zero
+       mknod random c 1 8;  chmod 0666 random
+       mknod urandom c 1 9; chmod 0444 urandom
+       mknod tty c 5 0;     chmod 0666 tty
+       mknod console c 5 1; chmod 0600 console
+       mknod ptmx c 5 2;    chmod 0666 ptmx
+       ln -sf /proc/self/fd/0 stdin
+       ln -sf /proc/self/fd/1 stdout
+       ln -sf /proc/self/fd/2 stderr
+    )
+}
+export -f make_device_nodes
+export target
+
+if [ $(id -u) -ne 0 ]; then
     fakeroot -s "$target"/fakeroot.log \
-    fakechroot -s \
+    make_device_nodes
+else
+    make_device_nodes
+fi
+
+repos=febootstrap
+if [ -n "$addrepo" ]; then
+    repos="$repos,$addrepo"
+fi
+
+# Run yum.
+run_yum ()
+{
     yum \
-       -c "$tmpdir"/febootstrap.repo \
-       $yumargs \
+       -y -c "$tmpdir"/febootstrap.repo \
+       --disablerepo=* --enablerepo=$repos \
+       --noplugins --nogpgcheck \
        --installroot="$target" \
-       install "${packages[@]}"
+       install "$@"
+}
+export -f run_yum
+export tmpdir
+export repos
+
+if [ $(id -u) -ne 0 ]; then
+    # Bash doesn't support exporting array variables, hence this
+    # tortuous workaround.
+    fakeroot -i "$target"/fakeroot.log -s "$target"/fakeroot.log \
+    fakechroot -s \
+    bash -c 'run_yum "$@"' run_yum "${packages[@]}"
+else
+    run_yum "${packages[@]}"
+fi
+
+# Clean up the yum repository.
+# XXX We shouldn't just rm files.
+if [ "$clean" = "yes" ]; then
+    rm -rf "$target"/var/cache/yum/febootstrap
+    rm -rf "$target"/var/cache/yum/febootstrap-updates
 fi