213 lines
6.3 KiB
Bash
Executable file
213 lines
6.3 KiB
Bash
Executable file
#!/bin/sh
|
|
# Copyright (c) 2017, 2021, 2023 Jonas 'Sortie' Termansen.
|
|
#
|
|
# Permission to use, copy, modify, and distribute this software for any
|
|
# purpose with or without fee is hereby granted, provided that the above
|
|
# copyright notice and this permission notice appear in all copies.
|
|
#
|
|
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
|
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
|
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
|
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
|
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
|
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
|
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
|
#
|
|
# tix-upgrade
|
|
# Upgrade operating system and ports.
|
|
|
|
set -e
|
|
|
|
cachedir=""
|
|
clean=false
|
|
collection=""
|
|
download_only=false
|
|
fetch_options=
|
|
ports_only=false
|
|
sysroot=""
|
|
upgrade_ports=false
|
|
upgrade_system=false
|
|
wait=""
|
|
|
|
dashdash=
|
|
previous_option=
|
|
for argument do
|
|
if test -n "$previous_option"; then
|
|
eval $previous_option=\$argument
|
|
previous_option=
|
|
shift
|
|
continue
|
|
fi
|
|
|
|
case $argument in
|
|
*=?*) parameter=$(expr "X$argument" : '[^=]*=\(.*\)' || true) ;;
|
|
*=) parameter= ;;
|
|
*) parameter=yes ;;
|
|
esac
|
|
|
|
case $dashdash$argument in
|
|
--) dashdash=yes ;;
|
|
-w) wait=-w ;;
|
|
--cachedir=*) cachedir=$parameter ;;
|
|
--cachedir) previous_option=cachedir ;;
|
|
--clean) clean=true ;;
|
|
--collection=*) collection=$parameter ;;
|
|
--collection) previous_option=collection ;;
|
|
--download-only) download_only=true ;;
|
|
--insecure-downgrade-to-http) fetch_options="$fetch_options $argument" ;;
|
|
--insecure-no-check-certificate) fetch_options="$fetch_options $argument" ;;
|
|
--ports) upgrade_ports=true ;;
|
|
--system) upgrade_system=true ;;
|
|
--sysroot) previous_option=sysroot ;;
|
|
--sysroot=*) sysroot=$parameter ;;
|
|
--wait) wait=--wait ;;
|
|
-*) echo "$0: unrecognized option $argument" >&2
|
|
exit 1 ;;
|
|
*) break ;;
|
|
esac
|
|
|
|
shift
|
|
done
|
|
|
|
if test -n "$previous_option"; then
|
|
echo "$0: option '$argument' requires an argument" >&2
|
|
exit 1
|
|
fi
|
|
|
|
# TODO: Reject additional operands.
|
|
|
|
if [ -z "$collection" ]; then
|
|
collection="$sysroot"
|
|
fi
|
|
|
|
if [ -n "$collection" ]; then
|
|
collection=$(cd "$collection" && pwd)
|
|
fi
|
|
|
|
if ! $upgrade_ports && ! $upgrade_system; then
|
|
# TODO: Ability to set default in /etc/upgrade.conf.
|
|
upgrade_ports=true
|
|
upgrade_system=true
|
|
fi
|
|
|
|
# Update only ports if this isn't a whole system installation.
|
|
if [ ! -e "$collection/tix/manifest/system" ]; then
|
|
upgrade_system=false
|
|
fi
|
|
|
|
if [ -z "$cachedir" ]; then
|
|
cachedir="$collection/var/cache/tix"
|
|
fi
|
|
|
|
if $clean; then
|
|
echo "Removing cache directory: $cachedir"
|
|
rm -rf -- "$cachedir"
|
|
fi
|
|
|
|
mkdir -p -- "$cachedir"
|
|
mkdir -p -- "$cachedir/new"
|
|
|
|
# Fetch the latest official release.sig.sh and its matching sha256sum file.
|
|
tix-fetch $fetch_options \
|
|
--collection="$collection" \
|
|
--output-release-sig-file="$cachedir/new/release.sh.sig" \
|
|
--output-sha256sum="$cachedir/new/sha256sum"
|
|
|
|
# If release.sig.sh or sha256sum changed, clean the cache directory of downloads
|
|
# that were currently in progress as they might not have the right checksums.
|
|
# TODO: This requires diff(1) in the base system! Avoid that. Get a cmp(1)!
|
|
if ! diff -- "$cachedir/release.sh.sig" \
|
|
"$cachedir/new/release.sh.sig" 1>/dev/null 2>/dev/null ||
|
|
! diff -- "$cachedir/sha256sum" \
|
|
"$cachedir/new/sha256sum" 1>/dev/null 2>/dev/null; then
|
|
rm -rf -- "$cachedir/boot"
|
|
rm -rf -- "$cachedir/repository"
|
|
rm -rf -- "$cachedir/sysroot"
|
|
fi
|
|
|
|
# Store the new release.sig.sh and sha256sum files so we can resume the download
|
|
# if cancelled and these files still match.
|
|
mv -- "$cachedir/new/release.sh.sig" "$cachedir/release.sh.sig"
|
|
mv -- "$cachedir/new/sha256sum" "$cachedir/sha256sum"
|
|
rm -rf -- "$cachedir/new"
|
|
|
|
mkdir -p "$cachedir/boot"
|
|
mkdir -p "$cachedir/repository"
|
|
|
|
# TODO: Support upgrading across releases, renamed channels, etc.
|
|
|
|
if $upgrade_system; then
|
|
# Fetch the base system initrds from the mirror.
|
|
# TODO: What about the system source code in /src?
|
|
# TODO: Get the overlay initrd if it exists.
|
|
tix-fetch $fetch_options \
|
|
--collection="$collection" \
|
|
--input-release-sig-file="$cachedir/release.sh.sig" \
|
|
--input-sha256sum="$cachedir/sha256sum" \
|
|
-c --initrd -O "$cachedir/boot" -- system
|
|
fi
|
|
|
|
if $upgrade_ports; then
|
|
# Fetch each port from the mirror.
|
|
ports=$(LC_ALL=C ls -- "$collection/tix/tixinfo")
|
|
# TODO: Handle new mandatory / recommended ports.
|
|
# TODO: Handle renamed ports.
|
|
# TODO: This fails if the port does not exist upstream.
|
|
mkdir -p "$cachedir/repository"
|
|
for port in $ports; do
|
|
# The port has a hash if if it exists upstream.
|
|
sha256=$(tix-fetch $fetch_options \
|
|
--collection="$collection" \
|
|
--input-release-sig-file="$cachedir/release.sh.sig" \
|
|
--input-sha256sum="$cachedir/sha256sum" \
|
|
--sha256 --port -- $port)
|
|
# If the port exists upstream, get the latest version.
|
|
if [ -n "$sha256" ]; then
|
|
tix-fetch $fetch_options \
|
|
--collection="$collection" \
|
|
--input-release-sig-file="$cachedir/release.sh.sig" \
|
|
--input-sha256sum="$cachedir/sha256sum" \
|
|
-c --port -O "$cachedir/repository" -- $port
|
|
fi
|
|
done
|
|
fi
|
|
|
|
# Stop if only downloading.
|
|
if $download_only; then
|
|
exit
|
|
fi
|
|
|
|
rm -rf -- "$cachedir/sysroot"
|
|
mkdir -p -- "$cachedir/sysroot"
|
|
|
|
# Extract the base system into the sysroot.
|
|
if $upgrade_system; then
|
|
echo "Extracting system.tar.xz..."
|
|
tar -C "$cachedir/sysroot" -xJf "$cachedir/boot/system.tar.xz"
|
|
rm -f "$cachedir/boot/system.tar.xz"
|
|
fi
|
|
|
|
# Extract the ports into the sysroot.
|
|
full=
|
|
if $upgrade_ports; then
|
|
full=--full
|
|
for port in $ports; do
|
|
echo "Extracting $port.tix.tar.xz..."
|
|
tar -C "$cachedir/sysroot" -xJf "$cachedir/repository/$port.tix.tar.xz"
|
|
rm -f "$cachedir/repository/$port.tix.tar.xz"
|
|
done
|
|
fi
|
|
|
|
case "$upgrade_system$upgrade_ports" in
|
|
truefalse) what_to_upgrade=--system;;
|
|
falsetrue) what_to_upgrade=--ports;;
|
|
*) what_to_upgrade=;;
|
|
esac
|
|
|
|
# Merge the new sysroot onto the installation.
|
|
sysmerge -t "$collection" $what_to_upgrade $full $wait "$cachedir/sysroot"
|
|
|
|
rm -rf -- "$cachedir/boot"
|
|
rm -rf -- "$cachedir/repository"
|
|
rm -rf -- "$cachedir/sysroot"
|