mirror of
https://github.com/MCKero6423/uv-k5-v3-emulator.git
synced 2026-10-02 03:15:36 +00:00
flash controller: store ACR/OPTKEYR instead of swallowing them, which is what stopped the factory bootloader from starting slots over the firmware's own serial protocol (0x0720 family); uvk5_socket/uvk5_testenv so a fresh checkout skips instead of failing; web UI slot table and Multiboot button; quick start, CONTRIBUTING, and stop tracking firmware images and radio dumps
115 lines
4.6 KiB
Bash
Executable File
115 lines
4.6 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# Run every test, report what failed, and exit non-zero if anything did.
|
|
#
|
|
# This exists because the suite had grown to ten separate invocations that had to be
|
|
# remembered and pasted in the right order. That is how regressions slip through: it is
|
|
# too easy to run the two tests related to what you just changed and miss the one that
|
|
# broke.
|
|
#
|
|
# Emulator tests boot their own QEMU and take 20-30 s each, so a full run is a few
|
|
# minutes. Pass -q to run only the fast unit tests, which need no emulator at all and
|
|
# finish in about 15 s -- useful while iterating.
|
|
#
|
|
# The build is checked FIRST and a failure stops everything. ninja leaves the previous
|
|
# binary in place when it fails, so the tests would otherwise run happily against a
|
|
# stale build and report results for code that was never compiled. That has produced
|
|
# two rounds of meaningless output before now.
|
|
set -u
|
|
|
|
HERE=$(cd "$(dirname "$0")" && pwd)
|
|
SIM=$(dirname "$HERE")
|
|
QEMU_SRC=${QEMU_SRC:-/root/qemu-build/qemu-7.2+dfsg}
|
|
|
|
# One interpreter name, resolved once. This script used to spell $PY on every
|
|
# line, which is a Windows problem (there is a python, not a python3) and a
|
|
# virtualenv problem alike -- and a runner that cannot start is indistinguishable
|
|
# from a runner that passes, which is the failure mode this script exists to avoid.
|
|
PY=${PYTHON:-}
|
|
if [ -z "$PY" ]; then
|
|
for candidate in $PY python; do
|
|
if command -v "$candidate" >/dev/null 2>&1; then PY=$candidate; break; fi
|
|
done
|
|
fi
|
|
[ -n "$PY" ] || { echo "no $PY or python on PATH; set PYTHON=/path/to/python" >&2; exit 1; }
|
|
|
|
QUICK=0
|
|
[ "${1:-}" = "-q" ] && QUICK=1
|
|
|
|
pass=0
|
|
fail=0
|
|
failed_names=""
|
|
|
|
run() {
|
|
local name="$1"; shift
|
|
printf '\n=== %s\n' "$name"
|
|
# Strip control characters. Some tests shell out to gdb, whose output can carry
|
|
# escape sequences and stray bytes; left alone they make the combined log a
|
|
# "binary file" as far as grep is concerned, which silently swallows the summary.
|
|
#
|
|
# PIPESTATUS, not $?, because $? here is sed's status and would report success
|
|
# for every failing test.
|
|
"$@" 2>&1 | tr -cd '\11\12\15\40-\176' | sed 's/^/ /'
|
|
if [ "${PIPESTATUS[0]}" = "0" ]; then
|
|
pass=$((pass + 1))
|
|
else
|
|
fail=$((fail + 1))
|
|
failed_names="$failed_names $name"
|
|
fi
|
|
}
|
|
|
|
# --- build ---------------------------------------------------------------
|
|
# Only when the model source differs from what the QEMU tree holds, so a plain test
|
|
# run does not pay for a rebuild it does not need.
|
|
if [ -d "$QEMU_SRC/build" ] && \
|
|
! cmp -s "$SIM/qemu/py32f071.c" "$QEMU_SRC/hw/arm/py32f071.c"; then
|
|
echo "=== build (model source changed)"
|
|
cp "$SIM/qemu/py32f071.c" "$QEMU_SRC/hw/arm/py32f071.c"
|
|
if (cd "$QEMU_SRC/build" && ninja qemu-system-arm 2>&1 | tail -20) \
|
|
| grep -qE 'FAILED|error:'; then
|
|
echo " BUILD FAILED -- stopping before any test runs"
|
|
echo " (a stale binary would otherwise be tested silently)"
|
|
exit 1
|
|
fi
|
|
echo " ok"
|
|
fi
|
|
|
|
# --- unit tests, no emulator --------------------------------------------
|
|
cd "$HERE"
|
|
# First, that this script itself reports failures. A runner that silently counts every
|
|
# test as passing is worse than no runner, because it gets trusted.
|
|
run "runner self-check" bash "$HERE/test_run_tests.sh"
|
|
run "docs match code" $PY "$HERE/check_docs.py"
|
|
run "unit: model helpers" $PY -m unittest discover -p 'test_uvk5*.py' -q
|
|
run "unit: web UI" $PY -m unittest test_webui -q
|
|
|
|
if [ "$QUICK" = "1" ]; then
|
|
printf '\n%d passed, %d failed (unit tests only)\n' "$pass" "$fail"
|
|
[ "$fail" = "0" ] || { echo "failed:$failed_names"; exit 1; }
|
|
exit 0
|
|
fi
|
|
|
|
# --- emulator tests -----------------------------------------------------
|
|
# Ordered cheapest first, so an obvious breakage surfaces without waiting for the
|
|
# whole run.
|
|
cd "$SIM"
|
|
run "keypad" $PY tools/keypad_test.py
|
|
run "BK4819 registers" $PY tools/test_bk4819.py
|
|
run "register readback" bash tools/test_bk4819_readback.sh
|
|
run "S-meter" $PY tools/test_smeter.py
|
|
run "PTT" $PY tools/test_ptt.py
|
|
run "scan" $PY tools/test_scan.py
|
|
run "audio path" $PY tools/test_audio_path.py
|
|
run "battery" $PY tools/test_battery.py
|
|
run "millis" $PY tools/test_millis.py
|
|
run "spectrum" $PY tools/test_spectrum.py
|
|
run "serial receive" $PY tools/test_serial_rx.py
|
|
run "slot over serial" $PY tools/test_slot_serial.py
|
|
run "flash persistence" $PY tools/test_flash_persist.py
|
|
run "frequency entry" $PY tools/test_freq_entry.py
|
|
|
|
printf '\n%d passed, %d failed\n' "$pass" "$fail"
|
|
if [ "$fail" != "0" ]; then
|
|
echo "failed:$failed_names"
|
|
exit 1
|
|
fi
|