130 lines
5.5 KiB
Bash
Executable File
130 lines
5.5 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
set -euo pipefail
|
|
|
|
ROOT=$(cd "$(dirname "$0")/.." && pwd)
|
|
source "$ROOT/Scripts/sparkle_signing_paths.sh"
|
|
|
|
TEMP_DIR=$(mktemp -d "${TMPDIR:-/tmp}/codexbar-sparkle-signing.XXXXXX")
|
|
TEMP_DIR=$(cd "$TEMP_DIR" && pwd -P)
|
|
trap 'rm -rf "$TEMP_DIR"' EXIT
|
|
|
|
make_sparkle_version() {
|
|
local sparkle="$1"
|
|
local version="$2"
|
|
local version_dir="$sparkle/Versions/$version"
|
|
|
|
mkdir -p \
|
|
"$version_dir/Updater.app/Contents/MacOS" \
|
|
"$version_dir/XPCServices/Downloader.xpc/Contents/MacOS" \
|
|
"$version_dir/XPCServices/Installer.xpc/Contents/MacOS"
|
|
touch \
|
|
"$version_dir/Sparkle" \
|
|
"$version_dir/Autoupdate" \
|
|
"$version_dir/Updater.app/Contents/MacOS/Updater" \
|
|
"$version_dir/XPCServices/Downloader.xpc/Contents/MacOS/Downloader" \
|
|
"$version_dir/XPCServices/Installer.xpc/Contents/MacOS/Installer"
|
|
}
|
|
|
|
SINGLE="$TEMP_DIR/Single Sparkle.framework"
|
|
make_sparkle_version "$SINGLE" B
|
|
single_version=$(codexbar_sparkle_version_dir "$SINGLE")
|
|
[[ "$single_version" == "$SINGLE/Versions/B" ]]
|
|
|
|
single_targets=$(codexbar_sparkle_signing_targets "$SINGLE")
|
|
grep -Fqx "$SINGLE" <<<"$single_targets"
|
|
grep -Fqx "$SINGLE/Versions/B/Sparkle" <<<"$single_targets"
|
|
grep -Fqx "$SINGLE/Versions/B/XPCServices/Installer.xpc/Contents/MacOS/Installer" <<<"$single_targets"
|
|
|
|
CURRENT="$TEMP_DIR/Current Sparkle.framework"
|
|
make_sparkle_version "$CURRENT" A
|
|
make_sparkle_version "$CURRENT" C
|
|
ln -s C "$CURRENT/Versions/Current"
|
|
current_version=$(codexbar_sparkle_version_dir "$CURRENT")
|
|
[[ "$current_version" == "$CURRENT/Versions/C" ]]
|
|
|
|
rm "$CURRENT/Versions/C/Autoupdate"
|
|
if codexbar_sparkle_signing_targets "$CURRENT" >"$TEMP_DIR/missing-target.out" 2>"$TEMP_DIR/missing-target.log"; then
|
|
echo "ERROR: Missing Sparkle signing target was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "Autoupdate" "$TEMP_DIR/missing-target.log"
|
|
|
|
AMBIGUOUS="$TEMP_DIR/Ambiguous Sparkle.framework"
|
|
make_sparkle_version "$AMBIGUOUS" A
|
|
make_sparkle_version "$AMBIGUOUS" B
|
|
if codexbar_sparkle_version_dir "$AMBIGUOUS" 2>"$TEMP_DIR/ambiguous.log"; then
|
|
echo "ERROR: Ambiguous Sparkle versions were accepted without Versions/Current." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "multiple version directories" "$TEMP_DIR/ambiguous.log"
|
|
|
|
BROKEN_CURRENT="$TEMP_DIR/Broken Current Sparkle.framework"
|
|
make_sparkle_version "$BROKEN_CURRENT" B
|
|
ln -s Missing "$BROKEN_CURRENT/Versions/Current"
|
|
if codexbar_sparkle_version_dir "$BROKEN_CURRENT" 2>"$TEMP_DIR/broken-current.log"; then
|
|
echo "ERROR: Broken Sparkle Versions/Current was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "Versions/Current does not resolve" "$TEMP_DIR/broken-current.log"
|
|
|
|
ESCAPING_CURRENT="$TEMP_DIR/Escaping Current Sparkle.framework"
|
|
OUTSIDE_SPARKLE="$TEMP_DIR/Outside Sparkle.framework"
|
|
make_sparkle_version "$ESCAPING_CURRENT" B
|
|
make_sparkle_version "$OUTSIDE_SPARKLE" C
|
|
ln -s "$OUTSIDE_SPARKLE/Versions/C" "$ESCAPING_CURRENT/Versions/Current"
|
|
if codexbar_sparkle_version_dir "$ESCAPING_CURRENT" 2>"$TEMP_DIR/escaping-current.log"; then
|
|
echo "ERROR: Escaping Sparkle Versions/Current was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "outside the framework versions directory" "$TEMP_DIR/escaping-current.log"
|
|
|
|
SYMLINKED_VERSIONS="$TEMP_DIR/Symlinked Versions Sparkle.framework"
|
|
mkdir -p "$SYMLINKED_VERSIONS"
|
|
ln -s "$OUTSIDE_SPARKLE/Versions" "$SYMLINKED_VERSIONS/Versions"
|
|
if codexbar_sparkle_version_dir "$SYMLINKED_VERSIONS" 2>"$TEMP_DIR/symlinked-versions.log"; then
|
|
echo "ERROR: Symlinked Sparkle Versions directory was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "versions directory must not be a symlink" "$TEMP_DIR/symlinked-versions.log"
|
|
|
|
SYMLINKED_FRAMEWORK="$TEMP_DIR/Symlinked Sparkle.framework"
|
|
ln -s "$OUTSIDE_SPARKLE" "$SYMLINKED_FRAMEWORK"
|
|
if codexbar_sparkle_version_dir "$SYMLINKED_FRAMEWORK" 2>"$TEMP_DIR/symlinked-framework.log"; then
|
|
echo "ERROR: Symlinked Sparkle framework root was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "framework root must not be a symlink" "$TEMP_DIR/symlinked-framework.log"
|
|
|
|
SYMLINKED_TARGET="$TEMP_DIR/Symlinked Target Sparkle.framework"
|
|
make_sparkle_version "$SYMLINKED_TARGET" B
|
|
rm "$SYMLINKED_TARGET/Versions/B/Autoupdate"
|
|
ln -s "$OUTSIDE_SPARKLE/Versions/C/Autoupdate" "$SYMLINKED_TARGET/Versions/B/Autoupdate"
|
|
if codexbar_sparkle_signing_targets \
|
|
"$SYMLINKED_TARGET" >"$TEMP_DIR/symlinked-target.out" 2>"$TEMP_DIR/symlinked-target.log"; then
|
|
echo "ERROR: Symlinked Sparkle signing target was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "signing target must not be a symlink" "$TEMP_DIR/symlinked-target.log"
|
|
|
|
ESCAPING_TARGET_PARENT="$TEMP_DIR/Escaping Target Parent Sparkle.framework"
|
|
make_sparkle_version "$ESCAPING_TARGET_PARENT" B
|
|
mv "$ESCAPING_TARGET_PARENT/Versions/B/XPCServices" "$TEMP_DIR/displaced-xpc-services"
|
|
ln -s "$OUTSIDE_SPARKLE/Versions/C/XPCServices" "$ESCAPING_TARGET_PARENT/Versions/B/XPCServices"
|
|
if codexbar_sparkle_signing_targets \
|
|
"$ESCAPING_TARGET_PARENT" >"$TEMP_DIR/escaping-target-parent.out" 2>"$TEMP_DIR/escaping-target-parent.log"; then
|
|
echo "ERROR: Sparkle signing target with an escaping parent was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "signing target resolves outside its trusted root" "$TEMP_DIR/escaping-target-parent.log"
|
|
|
|
ESCAPING_SINGLE="$TEMP_DIR/Escaping Single Sparkle.framework"
|
|
mkdir -p "$ESCAPING_SINGLE/Versions"
|
|
ln -s "$OUTSIDE_SPARKLE/Versions/C" "$ESCAPING_SINGLE/Versions/B"
|
|
if codexbar_sparkle_version_dir "$ESCAPING_SINGLE" 2>"$TEMP_DIR/escaping-single.log"; then
|
|
echo "ERROR: Escaping single Sparkle version directory was accepted." >&2
|
|
exit 1
|
|
fi
|
|
grep -Fq "outside the framework versions directory" "$TEMP_DIR/escaping-single.log"
|
|
|
|
echo "Sparkle signing path tests passed."
|