From ba3d5191890acd7674995de0969a943803591a7b Mon Sep 17 00:00:00 2001 From: Abdessamad Derraz <3028866+Abdess@users.noreply.github.com> Date: Fri, 23 Oct 2026 17:06:54 +0200 Subject: [PATCH] docs: explain setups without a ZIP FAQ entry, the release_pack field and how to revisit it from download counts, the get/ pages, and RetroPie 4.8 now installs from a computer with the Pi's network folder as --dest. The start pages are back under their word ceilings. --- wiki/adding-a-platform.md | 7 ++++++ wiki/faq.md | 46 ++++++++++++++++++++------------------- wiki/first-install.md | 18 +++++++-------- wiki/glossary.md | 3 ++- wiki/installer.md | 12 +++++----- wiki/reference-terms.md | 3 ++- wiki/release-process.md | 46 +++++++++++++++++++++++++++++++++++---- wiki/testing-guide.md | 2 +- wiki/troubleshooting.md | 21 ++++++++---------- 9 files changed, 101 insertions(+), 57 deletions(-) diff --git a/wiki/adding-a-platform.md b/wiki/adding-a-platform.md index 607787b2..bed3b080 100644 --- a/wiki/adding-a-platform.md +++ b/wiki/adding-a-platform.md @@ -160,6 +160,7 @@ platforms: myplatform: config: myplatform.yml # platform YAML filename in platforms/ status: active # active or archived + release_pack: true # optional: a release publishes its ZIP device_group: handheld # computer, gaming-os, handheld, fpga or server scraper: myplatform # matches PLATFORM_NAME, null if hand-maintained schedule: weekly # re-scrape cadence, run by hand: weekly, monthly, or null @@ -682,6 +683,12 @@ A new platform is archived-by-default nowhere: `status: active` puts it in `status: archived` to keep the configuration without the automation. Archived platforms are excluded unless `--all` or `--include-archived` is passed. +A new platform has no release ZIP: `release_pack: true` is set for the setups +most people download, and the installer serves every other one from its +manifest. `generate_pack.py --platform myplatform` still builds its pack. +[Which platforms get a pack](release-process.md#which-platforms-get-a-pack) +says how the list is read from download counts. + Check the output for: - The new platform appears in verify results diff --git a/wiki/faq.md b/wiki/faq.md index f9109a35..bd5c0b6f 100644 --- a/wiki/faq.md +++ b/wiki/faq.md @@ -9,13 +9,13 @@ order: 50 - **Yes** for PlayStation 1 and 2, Saturn and Neo Geo. - **Better with it** for Dreamcast: some games need it. -- **Usually not** for NES or Super Nintendo cartridges. +- **Usually not** for NES or Super Nintendo. [What is a BIOS?](what-are-bios-files.md) ## How do I know which BIOS I need? -Run the command with `--dry-run`. It lists the files, changing nothing. +Add `--dry-run`. It lists the files, changing nothing. ```sh @@ -24,23 +24,21 @@ curl -fsSL https://raw.githubusercontent.com/Abdess/retrobios/main/install.sh | ## Do I need every file of a console? -No. A console often has one BIOS per region. To keep only yours, add your -region, like `--region us`. +No. To keep only your region's BIOS, add it, like `--region us`. ## Does the BIOS set the game's language? -Rarely. It comes from the game. Some games follow the console's setting, like -Flycast's **Language** option. +Rarely. It comes from the game. Some games follow the console's setting, like Flycast's **Language** +option. ## Zip or unzip? { #zip-or-unzip } -Unzip the ZIP you downloaded into the folder your setup's page names. Keep +Unzip it into the folder your setup's page names. Leave the ZIPs inside zipped, like `neogeo.zip`. ## Does a BIOS work on every setup? -Usually. The command installs the version each setup expects, like its -`neogeo.zip`. +Usually. The command installs each setup's own version, like its `neogeo.zip`. ## My arcade game does not start @@ -50,35 +48,39 @@ Reference: [Which version each emulator reads](technical-faq.md#which-mame-versi ## Keys, firmware or BIOS? - **BIOS** or **firmware**: the console's own program, like `scph5501.bin`. -- Some newer consoles need a system update, like `PS3UPDAT.PUP`, installed from the +- Newer consoles need a system update, like `PS3UPDAT.PUP`, installed from the emulator's menu. - **Keys** unlock encrypted games, like `prod.keys` for Switch. ## Can I play without the BIOS? -Sometimes. Some emulators carry a stand-in, and some games then fail. +Sometimes, with an emulator's stand-in, but some games fail. ## Is the command safe? { #is-piping-the-installer-into-a-shell-safe } -- It stops if the installer does not match its expected fingerprint, then - checks each file before saving it. -- It writes in your BIOS folder, and for some emulators in your save folder. +- It stops if the installer does not match its expected fingerprint, and checks + each file. +- It writes in your BIOS folder, and for some emulators your save folder. - It never touches a game or a save. -- It keeps any file it replaces in `retrobios-backup`, next to your BIOS - folder. `--restore` puts it back. +- It keeps each file it replaces in `retrobios-backup`. `--restore` puts it + back. Read them first: [install.sh](https://github.com/Abdess/retrobios/blob/main/install.sh), [install.ps1](https://github.com/Abdess/retrobios/blob/main/install.ps1), [install.py](https://github.com/Abdess/retrobios/blob/main/install.py). -[How the installer checks itself](installer.md#what-the-bootstrap-does). ## Windows or my antivirus blocks the command -Download your setup's ZIP from [Get your files](../which-pack.md) instead. +Use your setup's ZIP, if it has one: [Get your files](../which-pack.md). + +## Why is there no ZIP for my setup? + +ZIPs are made for the setups most people download. The command installs every +setup's files and checks each one. `--dry-run` shows the list first. ## Fill an SD card from a computer? -Yes. Name your setup and the BIOS folder on the card. For RetroArch on a Switch +Yes. Name your setup and the card's BIOS folder. For RetroArch on a Switch card in drive `E:`: @@ -89,7 +91,7 @@ curl -fsSL https://raw.githubusercontent.com/Abdess/retrobios/main/install.sh \ ## No internet on the device? -Unzip your setup's ZIP into the folder its page names. To check each file, use +Fill its folder from a computer, as above, or unzip your ZIP and check it with `--from-pack`: [Without a network](installer.md#without-a-network-offline-install). ## My setup is not in the list @@ -100,11 +102,11 @@ Unzip your setup's ZIP into the folder its page names. To check each file, use ## Why is a file missing from the ZIP? -Some come with the emulator, so the ZIP leaves them out. +Some come with the emulator, so the ZIP skips them. ## My game shows a black screen -A BIOS file is often missing: [When a game does not start](troubleshooting.md). +Often a missing BIOS: [When a game does not start](troubleshooting.md). ## Is this legal? diff --git a/wiki/first-install.md b/wiki/first-install.md index f6a62a28..f99d6485 100644 --- a/wiki/first-install.md +++ b/wiki/first-install.md @@ -97,7 +97,7 @@ curl -fsSL https://raw.githubusercontent.com/Abdess/retrobios/main/install.sh | ## 4. Wait -You can stop with Ctrl+C at any time. Run the command again to carry on. +Ctrl+C stops it. Run the command again to carry on. ## 5. Read the last line @@ -120,7 +120,7 @@ Add `--check` to the same command. It changes nothing. curl -fsSL https://raw.githubusercontent.com/Abdess/retrobios/main/install.sh | sh -s -- --check ``` -All good when every file is present and none is wrong: +All good: ``` 109/109 present (109 verified, 0 wrong hash) @@ -130,8 +130,8 @@ An empty folder also shows `0 wrong hash`, with `0/109 present`. ## Undo -It keeps every file it replaces in a `retrobios-backup` folder, next to your -BIOS folder. The end of the run prints the line that puts them back. +Every file it replaces goes to a `retrobios-backup` folder next to your BIOS +folder. The last lines say how to put them back. ## If it stops @@ -150,8 +150,8 @@ The message shows the command that installs Python. Run it, then run the installer again. A RetroPie 4.8 image has Python 3.7.3, and its update command finds nothing -newer. Use the [RetroPie ZIP](../platforms/retropie.md#download) there, -unzipped into `~/RetroPie/BIOS/`. +newer. Run the command on a computer, with +`--platform retropie --dest \\RETROPIE\bios\`. ### Error: the downloaded installer does not match its expected fingerprint. @@ -159,13 +159,11 @@ The download was cut short. Nothing was changed. Run the command again. ### Cannot create ... -You do not have the right to write there. Do what the message says. It names -what to run. +You cannot write there. Do what the message says. ### Not enough space on the drive holding ... -It stopped before writing. Free some space, or use `--dest` to pick another -drive. +Nothing was written. Free some space, or pick another drive with `--dest`. ### The game still does not start diff --git a/wiki/glossary.md b/wiki/glossary.md index 75c966e7..6acb9644 100644 --- a/wiki/glossary.md +++ b/wiki/glossary.md @@ -22,7 +22,8 @@ order: 60 : The folder where your setup looks for BIOS files. **Pack** -: The ZIP file with every BIOS file for one setup. +: The ZIP file with every BIOS file for one setup. Made for the setups most + people download. **Platform** : A setup, as the project's data calls it. diff --git a/wiki/installer.md b/wiki/installer.md index daf32cc5..0f42777f 100644 --- a/wiki/installer.md +++ b/wiki/installer.md @@ -992,8 +992,8 @@ file rather than followed. `install.py` runs on the user's machine, often an older handheld, so it stays on Python 3.8 and the standard library alone. The RetroPie 4.8 images (`retropie-buster-4.8-*.img.gz`) are Debian Buster, whose `python3` is 3.7.3: -there the bootstrap stops before running anything, and the RetroPie pack from -the releases page is the way to install +there the bootstrap stops before running anything, and the way to install is +the command run on a computer with the Pi's network folder as `--dest` ([first install](first-install.md#error-python-38-or-newer-is-required)). Tests refuse any 3.9 syntax or API, and one runs the installer end to end under a real 3.8 interpreter, which CI installs beside 3.12 so the check cannot skip. @@ -1167,10 +1167,10 @@ left out. `scripts/download.py --list` and `scripts/download.sh --list` print the packs of a release. A pack's name lists every platform it serves. Releases up to -v2026.10.10 ship RetroArch and Lakka as one `RetroArch_Lakka` pack, and the -next ones give Lakka its own, since Lakka runs on Linux where two names that -differ by case are two files. The installer and the download scripts find the -right pack either way. +v2026.10.10 ship RetroArch and Lakka as one `RetroArch_Lakka` pack. Later +releases publish packs only for the setups most people download, so Lakka, +which runs on Linux where two names that differ by case are two files, is +served by the installer. The download scripts name the installer for a setup without a pack. Parts named `Pack.part1of2.zip` are ordinary ZIPs: unzip each one into the same folder, and check that all of them were downloaded. The name says how many diff --git a/wiki/reference-terms.md b/wiki/reference-terms.md index 7f892478..a42aeee4 100644 --- a/wiki/reference-terms.md +++ b/wiki/reference-terms.md @@ -14,7 +14,8 @@ everyday words (BIOS, emulator, core, hash) are in the [glossary](glossary.md). **Pack** : One ZIP file with every BIOS file a setup uses. A pack over 2 GB comes in - several parts, and every part is needed. + several parts, and every part is needed. A release publishes packs for the + setups the registry marks `release_pack`, and the installer serves the rest. **Profile and source_ref** : A profile records which files one emulator opens, read from its code. diff --git a/wiki/release-process.md b/wiki/release-process.md index 126467c1..0c519813 100644 --- a/wiki/release-process.md +++ b/wiki/release-process.md @@ -206,8 +206,9 @@ pipeline runs here, the archives are checked here, and `gh` uploads them. ```bash # 1. Full pipeline, online, so data directories and MAME/FBNeo hashes are -# fresh. --include-archived builds RetroPie too, archived but still served, -# and holds its pack to the same consistency and integrity checks. +# fresh. It builds the packs of the platforms marked release_pack (see +# "Which platforms get a pack" below) and the install manifests of every +# platform, RetroPie included with --include-archived. python scripts/pipeline.py --include-archived # 2. A release file must be under 2 GiB. A larger pack becomes parts that are @@ -276,6 +277,43 @@ gh release list --json tagName,createdAt \ | tail -n +2 | while read tag; do gh release delete "$tag" --yes --cleanup-tag; done ``` +## Which platforms get a pack { #which-platforms-get-a-pack } + +`release_pack: true` in `platforms/_registry.yml` is the list. `generate_pack.py +--all` builds those packs and no other, `--verify-packs` and the consistency +step of the pipeline check those, `release_record.py` refuses any other pack +in `dist/`, and `check_release.py` reports a marked platform without a pack. +The README, the download page, each setup page and the release notes read the +same field: a platform without it shows "No ZIP" and the command. Its install +manifest is written all the same, and `generate_pack.py --platform NAME` still +builds its pack for anyone who wants one. + +The list follows downloads. In v2026.10.10, part 1 of each pack was fetched +7,251 times for RetroArch, 2,909 for EmuDeck, 1,988 for RetroBat, 1,933 for +Batocera and 1,003 for RomM, then 751 for RetroPie, 642 for Recalbox, 516 for +RetroDECK, 450 for MiSTer, 386 for ROCKNIX and 361 for BizHawk. The first five +are 83% of downloads for 17 GB of the 35 GB all packs weighed. MiSTer stays +for its 17 MB. To revisit the list, read the counts of the latest release, +counting a whole pack or the first part of a split one, so each download +counts once: + +```bash +gh api repos/Abdess/retrobios/releases/latest --jq '.assets[] + | select(.name | test("_BIOS_Pack(\\.part1of[0-9]+)?\\.zip$")) + | "\(.download_count)\t\(.name)"' | sort -rn +``` + +Then add or remove the field and regenerate the README and the site. + +Every platform has a page at `get//` on the site, its permanent +download address. It lists the files of the pack the latest release holds, +read from `release.json`, or gives the command when there is no pack. The +README, the setup pages and the release notes link it, never an asset URL: +step 6 deletes the previous tag, and with it every link to its assets. Six of +the eight links one community wiki had to our packs answered 404 that way. +Committing `release.json` in step 5 rebuilds these pages, so the release +never touches them. + ## Verifying a release `SHA256SUMS.txt` is signed with a key used for nothing else. Its public half @@ -320,8 +358,8 @@ fingerprint, `SHA256:jUcTBhDS5DhmheXuVhAzh3pb04uI0caOAaiZzWXvrk4`. Rotating the key means committing the new public half to `allowed_signers` and keeping the retired line, so signatures on past releases keep verifying. -One pack per platform, the full one: the platform's list plus everything its -cores load. Platform-only and per-emulator packs are build options, not +One pack per platform marked `release_pack`, the full one: the platform's list +plus everything its cores load. Platform-only and per-emulator packs are build options, not release assets, since a lighter pack means a core that fails with no message. The release notes are written by `release_notes.py`: the install commands, the pack table and its parts sentence come from `release.json`, then what diff --git a/wiki/testing-guide.md b/wiki/testing-guide.md index 73858829..b70673a9 100644 --- a/wiki/testing-guide.md +++ b/wiki/testing-guide.md @@ -48,7 +48,7 @@ Every module in `tests/`, by the area it guards. | Core regression suites | synthetic | `test_e2e`, `test_audit_regressions`, `test_tool_messages` | | File resolution and identity | synthetic + collection | `test_adler32_resolution`, `test_agnostic_scan`, `test_agnostic_scan_mode`, `test_agnostic_scope`, `test_agnostic_substitute`, `test_archive_choice`, `test_archive_recipes`, `test_bios_companions`, `test_bundled_identity`, `test_casefold_cache`, `test_db_aliases`, `test_declared_names`, `test_derivations`, `test_directory_entries`, `test_extra_identity`, `test_foreign_tree`, `test_foreign_tree_names`, `test_frontend_digest`, `test_game_data_homonyms`, `test_hashing`, `test_identity`, `test_md5_pack_context`, `test_name_tiebreak`, `test_nec_filing`, `test_owner_resolution`, `test_path_suffix`, `test_resolution_evidence`, `test_sega_filing`, `test_shipped_content`, `test_twin_declarations`, `test_validated_choice`, `test_variant_choice`, `test_variant_identity`, `test_zipped_member` | | Verification, cross-reference and profile checks | synthetic + profiles | `test_bios_layout`, `test_cache_independent_counts`, `test_case_insensitive_platforms`, `test_checks_have_values`, `test_core_file_fills_declaration`, `test_core_size_refusal`, `test_cross_reference_sources`, `test_crypto_aes`, `test_crypto_unique_data`, `test_crypto_verify`, `test_entry_categories`, `test_file_consumers`, `test_fileless_audit`, `test_flycast_layout`, `test_gap_settlement`, `test_hidden_extras`, `test_launcher_aliases`, `test_launcher_layer`, `test_native_mode`, `test_no_case_collisions`, `test_path_conflict_status`, `test_path_null_copies`, `test_profile_checks`, `test_profile_repositories`, `test_romm_hash_rule`, `test_shared_groups`, `test_standalone_links`, `test_standalone_mode`, `test_undeclared_dedup`, `test_unplaced_extras`, `test_validation_scope`, `test_verify_all_dir`, `test_verify_emulator_evidence`, `test_verify_listing`, `test_verify_pack_choice`, `test_verify_release_asset` | -| Packs and manifests | synthetic + real packs | `test_artifact_lock`, `test_atomic_artifacts`, `test_batocera_cores`, `test_deterministic_zip`, `test_emulator_pack_counts`, `test_finalize_pack_names`, `test_large_file_cache`, `test_libretro_layout`, `test_manifest_entry`, `test_minui_platform`, `test_no_game_data`, `test_pack_conformance_dirs`, `test_pack_core_extras`, `test_pack_counts`, `test_pack_destinations`, `test_pack_failures`, `test_pack_file_names`, `test_pack_grouping`, `test_pack_integrity`, `test_pack_member_identity`, `test_pack_readme`, `test_platform_inheritance`, `test_platform_keys`, `test_required_only_archives`, `test_required_only_twins`, `test_save_root`, `test_split_extras`, `test_split_names`, `test_split_pack`, `test_system_pack_extras`, `test_system_pack_parity`, `test_torrentzip`, `test_which_pack` | +| Packs and manifests | synthetic + real packs | `test_artifact_lock`, `test_atomic_artifacts`, `test_batocera_cores`, `test_deterministic_zip`, `test_emulator_pack_counts`, `test_finalize_pack_names`, `test_large_file_cache`, `test_libretro_layout`, `test_manifest_entry`, `test_minui_platform`, `test_no_game_data`, `test_pack_conformance_dirs`, `test_pack_core_extras`, `test_pack_counts`, `test_pack_destinations`, `test_pack_failures`, `test_pack_file_names`, `test_pack_grouping`, `test_pack_integrity`, `test_pack_member_identity`, `test_pack_readme`, `test_platform_inheritance`, `test_platform_keys`, `test_release_packs`, `test_required_only_archives`, `test_required_only_twins`, `test_save_root`, `test_split_extras`, `test_split_names`, `test_split_pack`, `test_system_pack_extras`, `test_system_pack_parity`, `test_torrentzip`, `test_which_pack` | | Slots and regions | synthetic + profiles | `test_region`, `test_region_agnostic_scan`, `test_region_groups`, `test_region_held`, `test_region_platform_index`, `test_region_required_only`, `test_slot`, `test_slots`, `test_slots_shipped_file` | | Hardware targets and systems | synthetic + target files | `test_extract_targets`, `test_lakka_targets`, `test_libretro_slugs`, `test_system_ids`, `test_system_selection`, `test_target_names`, `test_target_scrapers`, `test_target_systems`, `test_target_verify` | | Installer and downloads | loopback server | `test_check_release`, `test_download`, `test_install`, `test_install_cores`, `test_install_experience`, `test_install_offline`, `test_install_selection` | diff --git a/wiki/troubleshooting.md b/wiki/troubleshooting.md index fdbfaeb7..6ea973d2 100644 --- a/wiki/troubleshooting.md +++ b/wiki/troubleshooting.md @@ -24,25 +24,23 @@ Read the count line: 1/109 present (0 verified, 1 wrong hash) ``` -- **`wrong hash`**: another region, model, or damaged. Batocera says - `UNTESTED`. +- **`wrong hash`**: another region or model, or damaged. - **Fewer present than the total**: files are missing. - **A line under a file**, like `still zipped`, says what to fix. - **`0 wrong hash`, all present**: go to step 3. ## 2. Fix the files -Run it again without `--check`. It adds missing files and replaces wrong ones. +Run it without `--check`. It adds missing files and replaces wrong ones. ## 3. Check the folder and the names -- **Right folder?** [Get your files](../which-pack.md) names the one your setup - reads. +- **Right folder?** [Get your files](../which-pack.md) names it. - **Exact name?** `scph5501.bin` and `SCPH-5501.BIN` differ. On Linux, capitals count too. - **A `bios` folder inside your BIOS folder?** Move its files up one level. -- **Unzipped by hand on Linux?** Run the command once. It adds names that - differ by capitals only. +- **Unzipped by hand on Linux?** The command adds names that differ by + capitals. - **A ZIP in parts, like `Pack.part1of2.zip`?** Unzip every part into one folder. @@ -58,17 +56,16 @@ version. ## The BIOS is fine, the game still fails -- **Another emulator?** Each one reads its own files. Its page lists them. +- **Another emulator?** Each reads its own files, listed on its page. - **A BIOS setting?** Some emulators can skip the BIOS. In PCSX ReARMed, set **BIOS Selection** to **Auto**. -- **A disc game in several files?** Open its `.cue` or `.m3u` file, not a - `.bin`. +- **A disc in several files?** Open its `.cue` or `.m3u`, not a `.bin`. ## If the command fails { #installation-script-fails } - **Network error:** try again once github.com opens. -- **`The clock reads ...`:** the date is wrong. Let it sync over Wi-Fi, or set - it, then run again. +- **`The clock reads ...`:** the date is wrong. Sync it over Wi-Fi or set it, + then run again. - **Permission denied:** do what the message says. It names what to run. - **No setup found:** name it and its folder: