feat(quickemu): warn on unstable TSC for macOS Ventura+ on AMD

- Add check_macos_tsc_stability() to detect unstable TSC on Linux hosts
with
  AuthenticAMD CPUs when launching macOS Ventura+ guests
- Log a clear warning to the VM log and prompt interactively to continue
or
  abort to avoid guest freezes
- Abort by default in non-interactive mode to prevent unattended VM
hangs
- Add --ignore-tsc-warning to bypass the check and invoke the check
during
  vm_boot so it runs early in startup
Closes #1273

Signed-off-by: Martin Wimpress <martin@wimpress.org>
This commit is contained in:
Martin Wimpress 2026-01-24 15:15:37 +00:00 committed by Martin Wimpress
parent 086128530f
commit b0e643d1c3
1 changed files with 94 additions and 0 deletions

View File

@ -38,6 +38,94 @@ function ignore_msrs_alert() {
fi
}
# Check for TSC instability that can cause macOS Ventura+ to freeze on AMD Ryzen mobile CPUs.
# Returns 0 if check passes or user acknowledges warning, exits with 1 if user aborts.
# Reference: https://github.com/quickemu-project/quickemu/issues/1273
function check_macos_tsc_stability() {
# Gate 1: Only on Linux hosts
if [ "${OS_KERNEL}" != "Linux" ]; then
return 0
fi
# Gate 2: Only for AMD CPUs
if [ "${HOST_CPU_VENDOR}" != "AuthenticAMD" ]; then
return 0
fi
# Gate 3: Only for macOS guests
if [ "${guest_os}" != "macos" ]; then
return 0
fi
# Gate 4: Only for macOS Ventura (13) and newer
case ${macos_release} in
ventura|sonoma|sequoia|tahoe) ;;
*) return 0 ;;
esac
# Gate 5: Skip if user has already set tsc=reliable in kernel cmdline
local cmdline=""
if [ -r /proc/cmdline ]; then
cmdline=$(cat /proc/cmdline)
if [[ "${cmdline}" == *"tsc=reliable"* ]]; then
return 0
fi
fi
# Gate 6: Check if TSC is the current clocksource (indicates stable TSC)
local clocksource_path="/sys/devices/system/clocksource/clocksource0/current_clocksource"
local current_clocksource=""
if [ -r "${clocksource_path}" ]; then
current_clocksource=$(cat "${clocksource_path}")
if [ "${current_clocksource}" == "tsc" ]; then
return 0
fi
else
# Cannot determine clocksource - assume OK and let user discover issues
return 0
fi
# All gates failed - this system is at risk
# Check if warning should be skipped
if [ "${IGNORE_TSC_WARNING}" == "1" ]; then
echo " - TSC: WARNING! Unstable TSC detected (clocksource: ${current_clocksource})"
echo " Proceeding anyway due to --ignore-tsc-warning flag."
return 0
fi
# Display warning and prompt user
echo " - TSC: WARNING! Unstable TSC detected (clocksource: ${current_clocksource})"
echo " macOS ${macos_release^} may freeze on AMD Ryzen mobile CPUs."
echo
echo " Fix: Add 'tsc=reliable' to kernel boot parameters and reboot."
echo " Or: Use macOS Big Sur (11) or Monterey (12) instead."
echo " See: https://github.com/quickemu-project/quickemu/wiki/03-Create-macOS-virtual-machines#tsc-instability-on-amd-ryzen-mobile-cpus"
echo
# Log the warning
echo "TSC_WARNING: clocksource=${current_clocksource} macos_release=${macos_release} cpu_vendor=${HOST_CPU_VENDOR}" >> "${VMDIR}/${VMNAME}.log"
# Interactive prompt - check if stdin is a terminal
if [ -t 0 ]; then
echo -n "Do you want to continue anyway? [y/N] "
read -r response
case "${response}" in
[yY]|[yY][eE][sS])
echo " - TSC: Proceeding despite unstable TSC warning."
return 0
;;
*)
echo " - TSC: Aborting. Please apply one of the solutions above."
exit 1
;;
esac
else
# Non-interactive mode - abort by default for safety
echo "ERROR! Non-interactive mode detected. Use --ignore-tsc-warning to bypass this check."
exit 1
fi
}
function delete_shortcut() {
local SHORTCUT_DIR="${HOME}/.local/share/applications"
if [ -e "${SHORTCUT_DIR}/${VMNAME}.desktop" ]; then
@ -1364,6 +1452,7 @@ function vm_boot() {
configure_cpu
configure_ram
check_macos_tsc_stability
configure_bios
configure_os_quirks
configure_storage
@ -1848,6 +1937,7 @@ function usage() {
echo " --display : Select display backend. 'sdl' (default), 'cocoa', 'gtk', 'none', 'spice' or 'spice-app'"
echo " --fullscreen : Starts VM in full screen mode (Ctl+Alt+f to exit)"
echo " --ignore-msrs-always : Configure KVM to always ignore unhandled machine-specific registers"
echo " --ignore-tsc-warning : Skip TSC stability warning for macOS VMs on AMD"
echo " --kill : Kill the VM process if it is running"
echo " --offline : Override all network settings and start the VM offline"
echo " --shortcut : Create a desktop shortcut"
@ -2110,6 +2200,7 @@ sound_duplex="${sound_duplex:-hda-micro}"
ACCESS=""
ACTIONS=()
BRAILLE=""
IGNORE_TSC_WARNING=""
CPU_PINNING=""
FULLSCREEN=""
MONITOR_CMD=""
@ -2202,6 +2293,9 @@ else
-ignore-msrs-always|--ignore-msrs-always)
ignore_msrs_always
exit;;
-ignore-tsc-warning|--ignore-tsc-warning)
IGNORE_TSC_WARNING="1"
shift;;
-kill|--kill)
ACTIONS+=(kill_vm)
shift;;