Files
Brian Degenhardt 112bc73c4c Android: take a card snapshot at launch, and offer the restore
Wires MemoryCardBackup into the app.

The snapshot is taken immediately before the emulation thread starts, in
MainActivityRuntime.start() and startBios(). At that instant the card file is not
open, so the copy cannot catch a half-finished write and there is no thread
timing to reason about. It also means the copy holds the card as it stood when
the player last finished successfully -- if this session is the one that breaks
things, the snapshot is clean by construction. Restoring then loses the current
session's saves, which is the trade a save-state slot already makes.

The BIOS boot gets one too: its memory card manager can format a card or delete
saves off it, so that session is worth a copy for the same reason a game is.

Launch also checks the cards it is about to mount. If one will not read AND a
verified backup exists, the boot is HELD and the prompt offers to put it back
before the game starts. That ordering is not cosmetic: once the console has
mounted a card it caches its own picture of the directory in guest memory, and a
restore underneath would be written straight over. "Start anyway" stays available
-- some people will want to format fresh -- and is remembered only for the launch
it was answered for.

The memory card screen gets a per-card Backups panel: the snapshots with their
date, size and the game that was running, a verified-or-suspect badge, restore,
back up now, and the automatic-backups switch. That manual path is the one that
actually matters, because the automatic offer cannot fire for the failure players
hit most -- a card that verifies perfectly while the save inside it is damaged.
Recognising that would mean understanding each game's save format.

Restore is refused while a game is running, for the cache reason above, and says
so rather than failing quietly.

A suspect snapshot is listed rather than hidden: the pre-restore copy of a broken
card is exactly what someone may need back.
2026-08-20 09:24:01 -07:00
..

ARMSX2

PlayStation 2 Emulator for Android based on the work of PCSX2

App version

The Android app version is configured in app/build.gradle.kts under android.defaultConfig:

versionCode = providers.gradleProperty("armsx2.versionCode").orNull?.toInt() ?: 1088
versionName = providers.gradleProperty("armsx2.versionName").orNull ?: "2.5.8"

Change versionName to the user-facing release version and increment the integer versionCode for every published APK or AAB. Release scripts can still override these defaults with -Parmsx2.versionName=... and -Parmsx2.versionCode=....

Android APK builds

Release/test APKs should be built with the universal page-size builder:

./tools/build-universal-page-apk.sh ~/Downloads/ARMSX2-Refresh-UniversalPage.apk

The script compiles both 4K and 16K ARM64 emucore variants, packages them into one APK, signs it, and verifies 16K zip alignment. This keeps one distributable APK working correctly on both older 4K-page devices and newer 16K-page devices.