From 012913720ca701ee3c73767183cb871fe87ebe7d Mon Sep 17 00:00:00 2001 From: Abdessamad Derraz <3028866+Abdess@users.noreply.github.com> Date: Fri, 16 Oct 2026 06:32:09 +0200 Subject: [PATCH] fix: check the beebem teletext font size --- emulators/beebem.yml | 5 ++-- tests/test_profile_checks.py | 56 ++++++++++++++++++++++++++++++++++++ 2 files changed, 59 insertions(+), 2 deletions(-) create mode 100644 tests/test_profile_checks.py diff --git a/emulators/beebem.yml b/emulators/beebem.yml index 72a1529a..aca83321 100644 --- a/emulators/beebem.yml +++ b/emulators/beebem.yml @@ -561,14 +561,15 @@ files: system: bbc-micro-b required: true bundled: true - size: 3456 + min_size: 3456 + validation: [size] md5: 007ba0c023740666e56f879f5d0d4461 sha1: 7d1d2a7321b21a237ad2c52afb21a432ce674967 note: > Read from the program directory. The only file whose absence stops the emulator: BuildMode7Font failure makes Initialise return false and Main.cpp then exits with status 1. - source_ref: "Src/BeebWin.cpp:491-502, Src/Main.cpp:62-66" + source_ref: "Src/Video.cpp:167-215, Src/BeebWin.cpp:491-502, Src/Main.cpp:62-66" - name: RelayOn.snd description: "Cassette relay engage sample" diff --git a/tests/test_profile_checks.py b/tests/test_profile_checks.py new file mode 100644 index 00000000..21c7ae1c --- /dev/null +++ b/tests/test_profile_checks.py @@ -0,0 +1,56 @@ +"""A profile's checks are the ones the emulator's code runs. + +Each case reads a profile from emulators/ and offers its entry files of +chosen sizes or contents, then compares the verdict with what the code at +the profile's pin does with the same file. The cases come from reading that +code: a check the code does not run rejects a file the emulator loads, and a +check left out lets through a file the emulator refuses. +""" + +from __future__ import annotations + +import sys +import tempfile +import unittest +from pathlib import Path + +import yaml + +REPO_ROOT = Path(__file__).resolve().parents[1] +sys.path.insert(0, str(REPO_ROOT / "scripts")) + +from validation import _build_validation_index, check_file_validation # noqa: E402 + + +def _profile(name: str) -> dict: + with open(REPO_ROOT / "emulators" / f"{name}.yml", encoding="utf-8") as fh: + return yaml.safe_load(fh) + + +class _Probe(unittest.TestCase): + """Offer a profile entry a file and read the verdict.""" + + def setUp(self): + self._tmp = tempfile.TemporaryDirectory() + self.addCleanup(self._tmp.cleanup) + + def accepts(self, emulator: str, name: str, data: bytes) -> bool: + index = _build_validation_index({emulator: _profile(emulator)}) + path = Path(self._tmp.name) / name + path.write_bytes(data) + return check_file_validation(str(path), name, index, emulators={emulator}) is None + + +class BeebEmTeletextFont(_Probe): + """BuildMode7Font reads 96 characters of 18 two-byte rows, 3456 bytes, + and returns false at the first EOF, which stops BeebEm at startup; + bytes past them are never read (Src/Video.cpp:167-215 at a982ba6).""" + + def test_short_is_refused_and_longer_is_read(self): + self.assertFalse(self.accepts("beebem", "Teletext.fnt", b"\0" * 100)) + self.assertTrue(self.accepts("beebem", "Teletext.fnt", b"\0" * 3456)) + self.assertTrue(self.accepts("beebem", "Teletext.fnt", b"\0" * 4000)) + + +if __name__ == "__main__": + unittest.main()