docs: rewrite half-dash asides in comments

Dropping the double-dash asides left 72 comments and docstrings with
half a dash glued to the next word ("shape -a size or a size range -is
all"). They now read as a colon, a comma or parentheses, and a prose
style test names any that comes back.
This commit is contained in:
Abdessamad Derraz committed 2026-10-20 09:17:10 +02:00
1 parent e424a35aee
commit 71b59eb2a3
22 files changed
+89 -71

No files matched your search

+1 -1
View File
@@ -5,7 +5,7 @@
1. Fork this repository
2. Place the file in `bios/Manufacturer/Console/filename`
3. Variants (alternate hashes for the same file): `bios/Manufacturer/Console/.variants/`
4. Open a Pull Request - hashes are verified automatically and reported as a comment
4. Open a pull request. Its hashes are checked automatically and reported in a comment
The [dump provenance](https://abdess.github.io/retrobios/provenance/) page lists catalogued dumps still
missing from the collection, with their hashes. A file matching one of those is
+2 -2
View File
@@ -31,8 +31,8 @@ def write_if_changed(
Compares new and existing content after stripping timestamp lines.
Returns True if the file was written, False if skipped (unchanged).
A caller that writes a file in two passes -a body, then the same body
wrapped in front matter -passes ``normalize`` to reduce both sides to the
A caller that writes a file in two passes (a body, then the same body
wrapped in front matter) passes ``normalize`` to reduce both sides to the
part it owns. Without it the second pass always sees a difference, the
file is rewritten, and the fresh timestamp defeats the comparison.
"""
+3 -3
View File
@@ -847,7 +847,7 @@ def _resolve_agnostic(
"""Any file of the right shape under the declared prefix.
Some cores accept whatever filename sits in their BIOS directory, so the
shape -a size or a size range -is all that identifies a candidate. A
shape (a size or a size range) is all that identifies a candidate. A
declared hash outranks that, and stops this step being reached.
"""
if not file_entry.get("agnostic") or has_strong_hash:
@@ -1557,7 +1557,7 @@ def resolve_local_file(
if valid:
primary = [c[0] for c in valid if "/.variants/" not in c[0]]
return (primary[0] if primary else valid[0][0]), "hash_mismatch"
# No candidate contains the zipped_file -fall through to step 5
# No candidate contains the zipped_file: fall through to step 5
elif not unsourceable:
ordered = _by_affinity([c[0] for c in candidates], file_entry, dest_hint)
primary = [c for c in ordered if "/.variants/" not in c]
@@ -2557,7 +2557,7 @@ import re
# Validation and mode filtering -extracted to validation.py for SoC.
# Validation and mode filtering: extracted to validation.py for SoC.
# Re-exported below for backward compatibility.
+1 -1
View File
@@ -75,7 +75,7 @@ def _rsa_verify_pkcs1v15_sha256(
) -> bool:
"""Verify RSA-2048 PKCS#1 v1.5 with SHA-256.
Pure Python -uses Python's native int for modular exponentiation.
Pure Python: uses Python's native int for modular exponentiation.
Reproduces CryptoPP::RSASS<PKCS1v15, SHA256>::Verifier.
"""
n = int.from_bytes(modulus, "big")
+4 -4
View File
@@ -122,7 +122,7 @@ def _plan_group_removals(
Records clone groups in *mame_clones* and returns the paths to remove.
"""
true_dupes_to_remove: list[str] = []
# Separate by filename -same name = true duplicate, different name = clone
# Separate by filename: same name = true duplicate, different name = clone
by_name: dict[str, list[str]] = defaultdict(list)
for p in paths:
by_name[os.path.basename(p)].append(p)
@@ -147,7 +147,7 @@ def _plan_group_removals(
]
true_dupes_to_remove.extend(p for p in variants if p not in holders)
# Different filenames, same content -need special handling
# Different filenames, same content: need special handling
unique_names = sorted(by_name.keys())
if len(unique_names) > 1:
# Check if these are all in MAME/Arcade dirs AND all ZIPs
@@ -171,7 +171,7 @@ def _plan_group_removals(
true_dupes_to_remove.append(p)
else:
# Non-MAME different names (e.g., 64DD_IPL_US.n64 vs IPL_USA.n64)
# Keep ALL -each name may be needed by a different emulator
# Keep ALL: each name may be needed by a different emulator
# Only remove true duplicates (same name in multiple dirs)
pass
@@ -223,7 +223,7 @@ def deduplicate(bios_dir: str, dry_run: bool = False) -> dict:
# Find the best canonical across all paths
all_paths = [p for p in paths if p not in true_dupes_to_remove]
if not all_paths:
# All copies were marked for removal -keep the best one
# All copies were marked for removal: keep the best one
all_paths_sorted = sorted(paths, key=path_priority)
all_paths = [all_paths_sorted[0]]
true_dupes_to_remove = [p for p in paths if p != all_paths[0]]
+2 -2
View File
@@ -994,7 +994,7 @@ def generate_pack(
# Emulator-level validation: informational only for platform packs.
# Platform verification (existence/md5) is the authority for pack status.
# Emulator checks are supplementary -logged but don't downgrade.
# Emulator checks are supplementary: logged but don't downgrade.
# When a discrepancy is found, try to find a file satisfying both.
if file_status.get(dedup_key) == "ok":
local_path, disagreement = validated_choice(
@@ -1145,7 +1145,7 @@ def generate_pack(
seen_parents,
)
# README.txt for users -personalized step-by-step per platform
# README.txt for users: personalized step-by-step per platform
num_systems = len(pack_systems)
_registry_path = Path(platforms_dir) / "_registry.yml"
_pack_registry: dict = {}
+1 -1
View File
@@ -689,7 +689,7 @@ def contributing_text(
1. Fork this repository
2. Place the file in `bios/Manufacturer/Console/filename`
3. Variants (alternate hashes for the same file): `bios/Manufacturer/Console/.variants/`
4. Open a Pull Request - hashes are verified automatically and reported as a comment
4. Open a pull request. Its hashes are checked automatically and reported in a comment
The [dump provenance]({link("provenance")}) page lists catalogued dumps still
missing from the collection, with their hashes. A file matching one of those is
+1 -1
View File
@@ -212,7 +212,7 @@ def resolve_file(
if path and status != "hash_mismatch":
return path, status
# Large files from GitHub release assets -tried when local file is
# Large files from GitHub release assets: tried when local file is
# missing OR has a hash mismatch (wrong variant on disk)
name = file_entry.get("name", "")
if file_entry.get("type") == "directory" or name.endswith("/"):
+20 -20
View File
@@ -30,12 +30,12 @@ SOURCE_URL = (
# Libretro cores that expect BIOS files in a subdirectory of system/.
# System.dat lists filenames flat, and the scraper prepends the prefix.
# ref: each core's libretro.c or equivalent -see platforms/README.md
# ref: each core's libretro.c or equivalent: see platforms/README.md
CORE_SUBDIR_MAP = {
"nec-pc-98": "np2kai", # libretro-np2kai/sdl/libretro.c
"sharp-x68000": "keropi", # px68k/libretro/libretro.c
"sega-dreamcast": "dc", # flycast/shell/libretro/libretro.cpp
"sega-dreamcast-arcade": "dc", # flycast -same subfolder
"sega-dreamcast-arcade": "dc", # flycast: same subfolder
}
SYSTEM_SLUG_MAP = {
@@ -252,11 +252,11 @@ class Scraper(BaseScraper):
systems[req.system]["files"].append(requirement_entry(req))
# Systems not in System.dat but needed for RetroArch -added via
# Systems not in System.dat but needed for RetroArch: added via
# shared groups in _shared.yml. The includes directive is resolved
# at load time by load_platform_config().
EXTRA_SYSTEMS = {
# ref: Vircon32/libretro.c -virtual console, single BIOS
# ref: Vircon32/libretro.c, virtual console, single BIOS
"vircon32": {
"files": [
{
@@ -269,7 +269,7 @@ class Scraper(BaseScraper):
"manufacturer": "Vircon",
"docs": "https://docs.libretro.com/library/vircon32/",
},
# ref: xrick/src/sysvid.c, xrick/src/data.c -game data archive
# ref: xrick/src/sysvid.c, xrick/src/data.c, game data archive
"xrick": {
"files": [
{
@@ -295,7 +295,7 @@ class Scraper(BaseScraper):
# Arcade BIOS present in the repo but absent from System.dat.
# FBNeo expects them in system/ or system/fbneo/.
# ref: fbneo/src/burner/libretro/libretro.cpp
# ref: fbneo/src/burner/libretro/libretro.cpp -search order:
# ref: fbneo/src/burner/libretro/libretro.cpp, search order:
# 1) romset dir 2) system/fbneo/ 3) system/
EXTRA_ARCADE_FILES = [
{"name": "namcoc69.zip", "destination": "namcoc69.zip", "required": True},
@@ -339,7 +339,7 @@ class Scraper(BaseScraper):
# Extra files missing from System.dat for specific systems.
# Each traced to the core's source code.
EXTRA_SYSTEM_FILES = {
# melonDS DS DSi mode -ref: JesseTG/melonds-ds/src/libretro.cpp
# melonDS DS DSi mode, ref: JesseTG/melonds-ds/src/libretro.cpp
"nintendo-ds": [
{
"name": "dsi_bios7.bin",
@@ -362,7 +362,7 @@ class Scraper(BaseScraper):
"required": True,
},
],
# bsnes SGB naming -ref: bsnes/target-libretro/libretro.cpp
# bsnes SGB naming, ref: bsnes/target-libretro/libretro.cpp
"nintendo-sgb": [
{
"name": "sgb.boot.rom",
@@ -370,13 +370,13 @@ class Scraper(BaseScraper):
"required": False,
},
],
# JollyCV -ref: jollycv/libretro.c
# JollyCV, ref: jollycv/libretro.c
"coleco-colecovision": [
{"name": "BIOS.col", "destination": "BIOS.col", "required": True},
{"name": "coleco.rom", "destination": "coleco.rom", "required": True},
{"name": "bioscv.rom", "destination": "bioscv.rom", "required": True},
],
# Kronos ST-V -ref: libretro-kronos/libretro/libretro.c
# Kronos ST-V, ref: libretro-kronos/libretro/libretro.c
"sega-saturn": [
{
"name": "stvbios.zip",
@@ -384,7 +384,7 @@ class Scraper(BaseScraper):
"required": True,
},
],
# PCSX ReARMed / Beetle PSX alt BIOS -ref: pcsx_rearmed/libpcsxcore/misc.c
# PCSX ReARMed / Beetle PSX alt BIOS, ref: pcsx_rearmed/libpcsxcore/misc.c
# docs say PSXONPSP660.bin (uppercase) but core accepts any case
"sony-playstation": [
{
@@ -393,7 +393,7 @@ class Scraper(BaseScraper):
"required": False,
},
],
# Dolphin GC -ref: DolphinLibretro/Boot.cpp:72-73,
# Dolphin GC, ref: DolphinLibretro/Boot.cpp:72-73,
# BootManager.cpp:200-217, CommonPaths.h:139 GC_IPL="IPL.bin"
# Core searches system/dolphin-emu/Sys/ for data and BIOS.
# System.dat gc-ntsc-*.bin names are NOT what Dolphin loads.
@@ -414,7 +414,7 @@ class Scraper(BaseScraper):
"destination": "dolphin-emu/Sys/GC/JAP/IPL.bin",
"required": False,
},
# DSP firmware -ref: Source/Core/Core/HW/DSPLLE/DSPHost.cpp
# DSP firmware, ref: Source/Core/Core/HW/DSPLLE/DSPHost.cpp
{
"name": "dsp_coef.bin",
"destination": "dolphin-emu/Sys/GC/dsp_coef.bin",
@@ -425,7 +425,7 @@ class Scraper(BaseScraper):
"destination": "dolphin-emu/Sys/GC/dsp_rom.bin",
"required": True,
},
# Fonts -ref: Source/Core/Core/HW/EXI/EXI_DeviceIPL.cpp
# Fonts, ref: Source/Core/Core/HW/EXI/EXI_DeviceIPL.cpp
{
"name": "font_western.bin",
"destination": "dolphin-emu/Sys/GC/font_western.bin",
@@ -437,8 +437,8 @@ class Scraper(BaseScraper):
"required": False,
},
],
# minivmac casing -ref: minivmac/src/MYOSGLUE.c
# doc says MacII.rom, repo has MacII.ROM -both work on case-insensitive FS
# minivmac casing, ref: minivmac/src/MYOSGLUE.c
# doc says MacII.rom, repo has MacII.ROM: both work on case-insensitive FS
"apple-macintosh-ii": [
{"name": "MacII.ROM", "destination": "MacII.ROM", "required": True},
],
@@ -458,7 +458,7 @@ class Scraper(BaseScraper):
# Inject shared group references for systems that have core-specific
# subdirectory requirements already defined in _shared.yml.
# Note: fuse/ prefix NOT injected for sinclair-zx-spectrum.
# Verified in fuse-libretro/src/compat/paths.c -core searches
# Verified in fuse-libretro/src/compat/paths.c, core searches
# system/ flat, not fuse/ subfolder. Docs are wrong on this.
# A group System.dat already covers entry for entry injects nothing
# (ep128emu, keropi and kronos were), and a correction made there
@@ -484,12 +484,12 @@ class Scraper(BaseScraper):
{"ref": "ppsspp-assets", "destination": "PPSSPP"},
],
# single buildbot ZIP contains both Databases/ and Machines/
# ref: libretro.c:1118-1119 -system_dir/Machines + system_dir/Databases
# ref: libretro.c:1118-1119, system_dir/Machines + system_dir/Databases
"microsoft-msx": [
{"ref": "bluemsx", "destination": ""},
],
# FreeIntv overlays -system/freeintv_overlays/<rom>.png
# ref: FreeIntv/src/libretro.c:273 -stbi_load from system dir
# FreeIntv overlays: system/freeintv_overlays/<rom>.png
# ref: FreeIntv/src/libretro.c:273, stbi_load from system dir
# ZIP contains FreeIntvTS_Overlays/ subfolder, cache preserves it
# pack destination maps cache root to system/freeintv_overlays
# so final path is system/freeintv_overlays/FreeIntvTS_Overlays/<rom>.png
+3 -3
View File
@@ -184,7 +184,7 @@ def _resolve_path(p: str) -> str:
def _extract_bios_entries(component_val: dict) -> list[dict]:
"""Extract BIOS entries from all three possible locations in a component.
No dedup here -dedup is done in fetch_requirements() with full
No dedup here: dedup is done in fetch_requirements() with full
(system, filename) key to avoid dropping valid same-filename entries
across different systems.
"""
@@ -368,13 +368,13 @@ class Scraper(BaseScraper):
if resolved.startswith("saves"):
continue
# Build destination -default to bios/ if no path specified
# Build destination: default to bios/ if no path specified
if resolved:
destination = f"{resolved}/{filename}"
else:
destination = f"bios/{filename}"
# MD5 handling -sanitize upstream errors
# MD5 handling: sanitize upstream errors
md5_raw = entry.get("md5", "")
if isinstance(md5_raw, list):
parts = [str(m).strip().lower() for m in md5_raw if m]
@@ -132,7 +132,7 @@ def _check_atom(
if tok.startswith('"'):
pos += 1
return True, pos
# Unknown token -treat as true to avoid false negatives
# Unknown token: treat as true to avoid false negatives
pos += 1
return True, pos
@@ -1,8 +1,8 @@
"""Scraper for EmuDeck emulator targets.
Sources:
SteamOS: dragoonDorise/EmuDeck -functions/EmuScripts/*.sh
Windows: EmuDeck/emudeck-we -functions/EmuScripts/*.ps1
SteamOS: dragoonDorise/EmuDeck, functions/EmuScripts/*.sh
Windows: EmuDeck/emudeck-we, functions/EmuScripts/*.ps1
"""
from __future__ import annotations
@@ -70,7 +70,7 @@ TARGETS: list[tuple[str, str, str]] = [
("dingux/miyoo-arm32/latest", "miyoo-arm32", "armv5"),
("webos/armv7a/latest", "webos-armv7a", "armv7"),
("webos/aarch64/latest", "webos-aarch64", "aarch64"),
# vita: only VPK bundles on buildbot -cores listed via libretro-super recipes
# vita: only VPK bundles on buildbot, cores listed via libretro-super recipes
]
# Recipe-based targets: (recipe_path_under_RECIPE_BASE_URL, target_name, architecture)
+2 -2
View File
@@ -3,7 +3,7 @@
Implements GF(2^233) field arithmetic, elliptic curve point operations,
and ECDSA-SHA256 verification for Nintendo 3DS OTP certificate checking.
Zero external dependencies -uses only Python stdlib.
Zero external dependencies: uses only Python stdlib.
Curve: sect233r1 (NIST B-233, SEC 2 v2)
Field: GF(2^233) with irreducible polynomial t^233 + t^74 + 1
@@ -83,7 +83,7 @@ def _gf_inv(a: int) -> int:
q ^= 1 << shift
temp ^= r << shift
remainder = temp
# Multiply q * s in GF(2)[x] (no reduction -working in polynomial ring)
# Multiply q * s in GF(2)[x] (no reduction: working in polynomial ring)
qs = 0
qt = q
st = s
+2 -2
View File
@@ -505,7 +505,7 @@ def generate_platform_truth(
sys_cov["profiled"].add(emu_name)
# Ensure all systems of resolved cores have entries (even with 0 files).
# This documents that the system is covered -the core was analyzed and
# This documents that the system is covered: the core was analyzed and
# needs no external files for this system.
for emu_name in cores_profiled:
profile = profiles[emu_name]
@@ -778,7 +778,7 @@ def diff_platform_truth(truth: dict, scraped: dict) -> dict:
else:
summary["systems_fully_covered"] += 1
# Truth systems not matched by any scraped system -all files missing
# Truth systems not matched by any scraped system: all files missing
for t_sid in sorted(truth_systems):
if t_sid in matched_truth:
continue
+5 -5
View File
@@ -23,7 +23,7 @@ from nativemode import SIZE_AND_ANY_HASH, digest_algorithm, hash_mismatch_exclud
from ziptools import check_inside_zip
# Validation types that require console-specific cryptographic keys.
# verify.py cannot reproduce these -size checks still apply if combined.
# verify.py cannot reproduce these: size checks still apply if combined.
_CRYPTO_CHECKS = frozenset({"signature", "crypto"})
@@ -216,7 +216,7 @@ def _build_validation_index(profiles: dict) -> dict[str, dict]:
index[fname]["max_size"] = (
max(cur, f["max_size"]) if cur is not None else f["max_size"]
)
# Hash checks -collect all accepted hashes as sets (multiple valid
# Hash checks: collect all accepted hashes as sets (multiple valid
# versions of the same file, e.g. MT-32 ROM versions)
if "crc32" in checks and f.get("crc32"):
crc_val = f["crc32"]
@@ -235,7 +235,7 @@ def _build_validation_index(profiles: dict) -> dict[str, dict]:
for h in values:
if str(h).strip():
index[fname][hash_type].add(str(h).strip().lower())
# Adler32 -stored as known_hash_adler32 field (not in validation: list
# Adler32: stored as known_hash_adler32 field (not in validation: list
# for Dolphin, but support it in both forms for future profiles)
adler_val = f.get("known_hash_adler32") or f.get("adler32")
for value in adler_val if isinstance(adler_val, list) else [adler_val] if adler_val else []:
@@ -370,7 +370,7 @@ def check_file_validation(
checks = entry["checks"]
pe = entry.get("per_emulator", {})
# Size checks -sizes is a set of accepted values
# Size checks: sizes is a set of accepted values
if "size" in checks:
actual_size = os.path.getsize(local_path)
if entry["sizes"] and actual_size not in entry["sizes"]:
@@ -384,7 +384,7 @@ def check_file_validation(
emus = _emulators_for_check("size", pe)
return f"size too large: max {entry['max_size']}, got {actual_size}", emus
# Hash checks -compute once, reuse for all hash types.
# Hash checks: compute once, reuse for all hash types.
# Each hash field is a set of accepted values (multiple valid ROM versions).
need_hashes = any(
h in checks and entry.get(h) for h in ("crc32", "md5", "sha1", "sha256")
+4 -4
View File
@@ -109,7 +109,7 @@ _REPO_PLATFORMS = os.path.join(os.path.dirname(__file__), "..", "platforms")
DEFAULT_EMULATORS_DIR = "emulators"
# Status model -aligned with Batocera BiosStatus (batocera-systems:967-969)
# Status model: aligned with Batocera BiosStatus (batocera-systems:967-969)
class Status:
@@ -420,8 +420,8 @@ def _candidate_verdict(
"""Whether a profile entry can be a gap, and whether it is settled.
Three answers. "keep" means it is a candidate. "settled" means something
has answered for it -the platform declares it, or the profile documents
it as unsourceable -so the same requirement reached from another profile
has answered for it (the platform declares it, or the profile documents
it as unsourceable), so the same requirement reached from another profile
must not be reconsidered. "skip" means it does not apply in this context,
which leaves it open for a profile where it does: the same file can be
libretro-only here and standalone-only there.
@@ -735,7 +735,7 @@ def find_exclusion_notes(
)
continue
# Count standalone-only files -but only report as excluded if the
# Count standalone-only files, but only report as excluded if the
# platform does NOT use this emulator in standalone mode
standalone_set = platform_standalone_set(config)
is_standalone = runs_standalone(emu_name, profile, standalone_set)
+1 -1
View File
@@ -171,7 +171,7 @@ class TestPackDeterminism(unittest.TestCase):
sha1 = hashlib.sha1(payload).hexdigest()
# A romset goes through the deterministic rebuild, which stages the
# archive in a temporary file. Copying that file into the pack took
# its mtime -the wall clock -so 348 members of the real Recalbox
# its mtime, the wall clock, so 348 members of the real Recalbox
# pack moved between two builds while every byte matched. Without a
# romset here the fixture never reaches that path.
romset = self.bios / "romset.zip"
+12 -12
View File
@@ -574,7 +574,7 @@ class TestE2E(unittest.TestCase):
"type": "libretro",
"systems": ["console-a", "sys-md5"],
"files": [
# Size validation -correct size (16 bytes = len(b"PRESENT_REQUIRED"))
# Size validation: correct size (16 bytes = len(b"PRESENT_REQUIRED"))
{
"name": "present_req.bin",
"required": True,
@@ -582,14 +582,14 @@ class TestE2E(unittest.TestCase):
"size": 16,
"source_ref": "test.c:10-20",
},
# Size validation -wrong expected size
# Size validation: wrong expected size
{
"name": "present_opt.bin",
"required": False,
"validation": ["size"],
"size": 9999,
},
# CRC32 validation -correct crc32
# CRC32 validation: correct crc32
{
"name": "correct_hash.bin",
"required": True,
@@ -597,7 +597,7 @@ class TestE2E(unittest.TestCase):
"crc32": "91d0b1d3",
"source_ref": "hash.c:42",
},
# CRC32 validation -wrong crc32
# CRC32 validation: wrong crc32
{
"name": "no_md5.bin",
"required": False,
@@ -611,28 +611,28 @@ class TestE2E(unittest.TestCase):
"validation": ["crc32"],
"crc32": "0179e92e",
},
# MD5 validation -correct md5
# MD5 validation: correct md5
{
"name": "correct_hash.bin",
"required": True,
"validation": ["md5"],
"md5": "4a8db431e3b1a1acacec60e3424c4ce8",
},
# SHA1 validation -correct sha1
# SHA1 validation: correct sha1
{
"name": "correct_hash.bin",
"required": True,
"validation": ["sha1"],
"sha1": "a2ab6c95c5bbd191b9e87e8f4e85205a47be5764",
},
# MD5 validation -wrong md5
# MD5 validation: wrong md5
{
"name": "alias_target.bin",
"required": False,
"validation": ["md5"],
"md5": "0000000000000000000000000000dead",
},
# Adler32 -known_hash_adler32 field
# Adler32: known_hash_adler32 field
{
"name": "present_req.bin",
"required": True,
@@ -646,7 +646,7 @@ class TestE2E(unittest.TestCase):
"min_size": 10,
"max_size": 100,
},
# Signature -crypto check we can't reproduce, but size applies
# Signature: crypto check we can't reproduce, but size applies
{
"name": "correct_hash.bin",
"required": True,
@@ -747,7 +747,7 @@ class TestE2E(unittest.TestCase):
yaml.dump(emu_mixed_agnostic, fh)
# ---------------------------------------------------------------
# THE TEST -one method per feature area, all using same fixtures
# THE TEST: one method per feature area, all using same fixtures
# ---------------------------------------------------------------
def test_01_resolve_sha1(self):
@@ -999,7 +999,7 @@ class TestE2E(unittest.TestCase):
config, self.emulators_dir, self.db, profiles
)
names = {u["name"] for u in undeclared}
# dd_covered.bin is a file entry, not data_dir content -still undeclared
# dd_covered.bin is a file entry, not data_dir content: still undeclared
self.assertIn("dd_covered.bin", names)
def test_44_cross_ref_skips_launchers(self):
@@ -2197,7 +2197,7 @@ class TestE2E(unittest.TestCase):
config = load_platform_config("test_existence", self.platforms_dir)
profiles = load_emulator_profiles(self.emulators_dir)
result = verify_platform(config, self.db, self.emulators_dir, profiles)
# Simulate --json filtering (non-OK only) -ground_truth must survive
# Simulate --json filtering (non-OK only): ground_truth must survive
filtered = [d for d in result["details"] if d["status"] != Status.OK]
for d in filtered:
self.assertIn("ground_truth", d)
+1 -1
View File
@@ -260,7 +260,7 @@ class CandidateVerdict(unittest.TestCase):
"""Whether a profile entry can be a gap, and whether it is settled.
The filter chain mixed two kinds of skip. A settled entry is answered for
-the platform declares it, the profile calls it unsourceable -so the same
(the platform declares it, the profile calls it unsourceable), so the same
requirement reached from another profile must not be reconsidered. A
skipped one merely does not apply here: the same file can be libretro-only
in one profile and standalone-only in another, and recording it from the
+18
View File
@@ -238,6 +238,24 @@ class NoClauseSemicolons(unittest.TestCase):
self._check(files, _python_prose)
def test_python_prose_has_no_lone_dash_asides(self):
"""Removing " -- " asides left 72 comments reading "shape -a size or
a size range -is all": half a dash glued to the next word. A command
line flag quoted in prose (MAME's -listxml) is not an aside, and a
quotation is left alone."""
lone = re.compile(r"[A-Za-z0-9,)] -(?!listxml\b|lr\b|sa\b)[a-z]{2,}")
offenders = [
f"{path.relative_to(ROOT)}: {line.strip()[:100]}"
for path in _tracked() if path.suffix == ".py"
for line in re.sub(
r'`[^`]*`|"[^"\n]*\n?[^"\n]*"',
"",
_python_prose(path.read_text(encoding="utf-8")).replace('"""', ""),
).splitlines()
if lone.search(line) and not re.search(r"\b(python|curl|unittest|sh)\b .* -", line)
]
self.assertEqual(offenders, [], "\n".join(offenders[:40]))
def test_schema_descriptions(self):
offenders = []
for path in sorted((ROOT / "schemas").glob("*.json")):
+2 -2
View File
@@ -286,8 +286,8 @@ diff .cache/upstream-native/myplatform/<their file> \
```
The export must not lose anything the platform already declares. If your
format carries code as well as data - a script, a C# database, a manifest
whose BIOS list sits beside launch configuration - say so with
format carries code as well as data (a script, a C# database, a manifest
whose BIOS list sits beside launch configuration), say so with
`needs_original()` and patch their file rather than writing a new one. An
exporter that regenerates such a file from BIOS data alone hands the
maintainer something that no longer runs.