Files
wiicompiled/Launcher/macos/setup.command
T
Michael G 5c76e2b0df feature: add apple silicon native macOS support (#81)
* feature: add apple silicon native macOS support - #81

* (macos): Fix crash

This fixes a crash when viewing the rear camera

* fix(macos): keep interpolated presentation on main thread

* fix(macos): supply Retro-WFC payload during setup

* perf(windows): compile out flat-memory fallback check

* remove duplicate smoke test

* test(macos): name and focus host platform tests

* fix(macos): validate Retro-WFC payload cache

* fix(payload): preserve staged file access failures

* Limit flat-page checks to variable-page hosts

---------

Co-authored-by: patchzyy <64382339+patchzyy@users.noreply.github.com>
2026-09-01 18:57:15 +02:00

141 lines
6.5 KiB
Bash
Executable File

#!/usr/bin/env bash
# Entry point bundled in WiiCompiled Setup.app. The package contains source and
# tools only; a user's own verified disc is extracted into Application Support.
set -euo pipefail
resources=$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)
workspace_source="$resources/workspace"
nodtool="$resources/tools/nodtool"
translator="$resources/tools/Translator.Cli"
cmake_bin="$resources/tools/cmake/bin/cmake"
ninja_bin="$resources/tools/ninja"
support_root="$HOME/Library/Application Support/WiiCompiled"
workspace="$support_root/BuildWorkspace"
products="$support_root/Products"
fail() { printf 'WiiCompiled Setup: %s\n' "$*" >&2; exit 1; }
notice() { /usr/bin/osascript -e "display dialog \"${1//\"/\\\"}\" buttons {\"OK\"} default button \"OK\" with icon caution" >/dev/null; }
usage() {
cat <<'EOF'
Usage: setup.command --game IMAGE [--retro-dir DIR] [--install-location {user|applications}]
Without arguments this script opens file pickers. It is normally launched by
WiiCompiled Setup.app, not run directly.
EOF
}
game=""; retro_dir=""; install_location=applications
while (($#)); do
case "$1" in
--game) game=${2:-}; shift 2 ;;
--retro-dir) retro_dir=${2:-}; shift 2 ;;
--install-location) install_location=${2:-}; shift 2 ;;
-h|--help) usage; exit 0 ;;
*) fail "unknown option: $1" ;;
esac
done
[[ "$install_location" == user || "$install_location" == applications ]] || fail '--install-location must be user or applications'
if [[ -z "$game" ]]; then
game=$(/usr/bin/osascript <<'APPLESCRIPT'
set selectedFile to choose file with prompt "Choose your clean Mario Kart Wii PAL (RMCP01) disc image"
POSIX path of selectedFile
APPLESCRIPT
) || exit 0
choice=$(/usr/bin/osascript -e 'button returned of (display dialog "Would you like to build Retro Rewind too?" buttons {"Base game only", "Choose Retro Rewind folder"} default button "Base game only")')
if [[ "$choice" == 'Choose Retro Rewind folder' ]]; then
retro_dir=$(/usr/bin/osascript <<'APPLESCRIPT'
set selectedFolder to choose folder with prompt "Choose the RetroRewind6 folder (or its parent folder)"
POSIX path of selectedFolder
APPLESCRIPT
) || exit 0
fi
fi
[[ -x "$nodtool" ]] || fail 'the packaged nodtool is missing or not executable'
[[ -x "$translator" ]] || fail 'the packaged Translator.Cli is missing or not executable'
[[ -x "$cmake_bin" && -x "$ninja_bin" ]] || fail 'the packaged CMake or Ninja tool is missing'
if ! /usr/bin/xcode-select -p >/dev/null 2>&1; then
notice 'Xcode Command Line Tools are required once to compile WiiCompiled. Click OK, complete the Apple installer, then run WiiCompiled Setup again.'
/usr/bin/xcode-select --install || true
exit 1
fi
mkdir -p "$support_root" "$products"
if [[ ! -d "$workspace/.git" && ! -f "$workspace/projects/mkwii/recomp.yml" ]]; then
printf 'Preparing the local build workspace...\n'
rm -rf "$workspace"
/usr/bin/ditto "$workspace_source" "$workspace"
fi
profile=base
build_args=(--workspace "$workspace" --game "$game" --nodtool "$nodtool" --output-dir "$products")
if [[ -n "$retro_dir" ]]; then
profile=both
# Online play needs the shared Retro-WFC payload. Keep it in the per-user
# support directory rather than the packaged app or build workspace, then
# verify its pinned signature before publishing it into the local cache.
retro_wfc_dir="$support_root/RetroWfcPayload"
retro_wfc_payload="$retro_wfc_dir/binary/payload.RMCPD00.bin"
if [[ -f "$retro_wfc_payload" ]] && ! "$translator" validate-retro-wfc-payload --directory "$retro_wfc_dir"; then
printf 'Discarding an invalid cached Retro-WFC payload...\n' >&2
rm -f "$retro_wfc_payload"
fi
if [[ ! -f "$retro_wfc_payload" ]]; then
printf 'Downloading the Retro-WFC payload needed for online play...\n'
mkdir -p "$retro_wfc_dir"
payload_stage=$(mktemp -d "$retro_wfc_dir/.payload-download.XXXXXX")
temporary_payload="$payload_stage/binary/payload.RMCPD00.bin"
mkdir -p "$(dirname "$temporary_payload")"
trap 'rm -rf "$payload_stage"' EXIT
/usr/bin/curl --fail --silent --show-error --connect-timeout 10 --max-time 30 \
--retry 1 --output "$temporary_payload" \
'http://nas.play.rwfc.net/payload?g=RMCPD00' || fail 'could not download the Retro-WFC payload needed for online play'
"$translator" validate-retro-wfc-payload --directory "$payload_stage" || \
fail 'downloaded Retro-WFC payload failed signature validation'
mkdir -p "$retro_wfc_dir/binary"
mv "$temporary_payload" "$retro_wfc_payload"
rmdir "$payload_stage/binary" "$payload_stage"
trap - EXIT
fi
build_args+=(--profile both --base-output-dir "$products" --retro-rewind-package-dir "$retro_dir" --retro-wfc-offline-dir "$retro_wfc_dir")
fi
"$workspace/Launcher/local-build-macos.command" "${build_args[@]}" --profile "$profile" --cmake "$cmake_bin" --ninja "$ninja_bin" --translator-bin "$translator"
config="$support_root/Config.toml"
toml_string() { printf '%s' "$1" | sed -e 's/\\\\/\\\\\\\\/g' -e 's/"/\\\\"/g'; }
set_path() {
local key=$1 value=$2 encoded line temporary
encoded=$(toml_string "$value"); line="$key = \"$encoded\""; temporary="$config.tmp"
touch "$config"
if grep -q '^[[:space:]]*\[paths\][[:space:]]*$' "$config"; then
awk -v key="$key" -v line="$line" '
/^[[:space:]]*\[paths\][[:space:]]*$/ { print; print line; inside = 1; next }
inside && /^[[:space:]]*\[/ { inside = 0 }
inside && $0 ~ "^[[:space:]]*" key "[[:space:]]*=" { next }
{ print }
' "$config" > "$temporary"
else
{ cat "$config"; printf '\n[paths]\n%s\n' "$line"; } > "$temporary"
fi
mv "$temporary" "$config"
}
set_path dvd_root "$workspace/Assets/DATA"
[[ -n "$retro_dir" ]] && set_path retro_rewind_root "$retro_dir"
destination="$HOME/Applications"
if [[ "$install_location" == applications ]]; then destination=/Applications; fi
install_app() {
local app=$1
[[ -d "$products/$app" ]] || return 0
if [[ "$destination" == /Applications ]]; then
command="mkdir -p /Applications && rm -rf '/Applications/$app' && ditto '$products/$app' '/Applications/$app'"
/usr/bin/osascript -e "do shell script \"$command\" with administrator privileges"
else
mkdir -p "$destination"; rm -rf "$destination/$app"; /usr/bin/ditto "$products/$app" "$destination/$app"
fi
}
install_app WiiCompiled.app
[[ "$profile" == both ]] && install_app RetroRewind.app
notice "Installation complete. Your apps are in $destination."