# kat5200

kat5200 is an emulator for the Atari 5200 and Atari 8-bit computers.

## Installing

| Platform | Install option |
| --- | --- |
| Windows | Run the Inno Setup installer, or unzip the portable package anywhere and run `kat5200.exe`. |
| Linux | Install your distro package if available, or build and run `sudo cmake --install build` as shown below. Flatpak is also supported. |
| macOS | Open the `.dmg` and drag `kat5200.app` to Applications. |
| Android | Install the built APK. Phones, tablets, Android TV / Google TV, and Fire TV devices are supported. |

## Install Notes

### macOS

The macOS `.app` may be blocked by Gatekeeper because it is not Developer ID
signed and notarized. After copying `kat5200.app` to Applications, you may need
to remove the download quarantine attribute:

```sh
xattr -dr com.apple.quarantine /Applications/kat5200.app
```

If you installed the app somewhere else, replace `/Applications/kat5200.app` with
that path. You can also try Control-clicking `kat5200.app` in Finder and choosing
**Open**, then confirming that you want to open it.

### Android

kat5200 is distributed as a directly installable APK, not through the Play Store.
The APK is still signed for Android installation, but Android treats it as an
unknown-app install because it did not come from the Play Store. Android may ask
you to allow the app that opens the APK, such as your browser or file manager,
to install unknown apps.

On most phones and tablets, this is under:

```text
Settings > Apps > Special app access > Install unknown apps
```

Choose the browser or file manager you are using, then allow installs from that
source. Developer mode is usually not required for normal APK sideloading. It is
only needed for USB/ADB installs on devices that require USB debugging. On
Android TV / Google TV and Fire TV devices, the setting name and location vary
by vendor; look for **Unknown sources**, **Install unknown apps**, or enable
Developer options only if you are installing with ADB.

## Build Common

CMake is the single source of truth on every platform. Out-of-source builds are
required, so build into a separate directory such as `build/`.

## Dependencies

Common to all platforms:

- SDL3 and SDL3_image, found via CMake CONFIG mode
- zlib
- libm
- CMake:
  - Native builds require CMake 3.16 or newer.
  - The macOS packaging script also requires CMake 3.16 or newer.
  - The Android Gradle build pins CMake 3.22.1.

The desktop OpenGL shader path has been removed. Desktop builds render through
SDL_GPU shader bundles and no longer link OpenGL. Only the Android build links
GLES (`GLESv2` / `EGL`).

Optional ROM-set download support uses a per-platform backend:

| Platform | Backend |
| --- | --- |
| Windows | WinHTTP, a system component |
| Linux/macOS | libcurl, when `find_package(CURL)` succeeds at configure time |
| Android | JNI `HttpURLConnection`; no extra library |

## Building on Windows

Use the MSYS2 UCRT64 environment.

Install the toolchain and libraries with `pacman`:

```sh
pacman -S --needed \
  mingw-w64-ucrt-x86_64-gcc \
  mingw-w64-ucrt-x86_64-cmake \
  mingw-w64-ucrt-x86_64-ninja \
  mingw-w64-ucrt-x86_64-pkgconf \
  mingw-w64-ucrt-x86_64-SDL3 \
  mingw-w64-ucrt-x86_64-SDL3_image \
  mingw-w64-ucrt-x86_64-zlib
```

`objdump`/binutils, used by the portable-packaging step below, ships with the GCC
toolchain.

Configure and build:

```sh
cmake -B build -G Ninja -DCMAKE_BUILD_TYPE=Release
cmake --build build -j4
```

Build a portable package. This bundles the MinGW runtime DLLs discovered by
reading the PE import tables with `objdump -p`.

```sh
cmake --build build --target kat5200-portable-package
```

Output:

```text
build/dist/kat5200-<ver>-win64-portable/
build/dist/kat5200-<ver>-win64-portable.zip
```

The target is defined in `src/CMakeLists.txt` for `WIN32 AND MINGW` and driven by
`cmake/package_msys_portable.cmake`.

To build the installer, compile `kat5200.iss` with Inno Setup. It is 64-bit only.
The script's `DistDir` points at
`build-ninja\dist\kat5200-<ver>-win64-portable`; adjust it to match your actual
build directory before compiling.

## Building on Linux

Install SDL3, SDL3_image, zlib, CMake, and a C compiler from your distro package
manager. Use the development or `-devel` packages. On older distros, SDL3 may
need to be built from source. libcurl is optional for ROM downloads.

Configure, build, and install with an FHS layout:

```sh
cmake -B build -DCMAKE_INSTALL_PREFIX=/usr -DCMAKE_BUILD_TYPE=Release
cmake --build build -j4
sudo cmake --install build
```

The install step, defined in `src/CMakeLists.txt`, places:

- the `kat5200` binary in `bin/`
- seed config, shader bundles, and a freshly built `profiles.zip` in
  `${KAT_DATADIR}`
- the icon, `.desktop` entry, and `.metainfo.xml` in the standard XDG locations

`${KAT_DATADIR}` defaults to `<prefix>/share/kat5200` and can be overridden.

Flatpak developer convenience targets are also available. They are not part of
the default build.

```sh
cmake --build build --target flatpak-install
cmake --build build --target flatpak-bundle
```

For a complete Linux release, configure a Release build and run the umbrella
target:

```sh
cmake -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build --target kat5200-release -j4
```

This builds the native app, the Flatpak, and a source bundle. Versioned output
is written to `build/dist/` as `kat5200-<version>.flatpak` and
`kat5200-<version>-src.zip`.

The Flatpak manifest is `flatpak/io.github.madjacket.kat5200.yml` and uses the
freedesktop runtime 25.08. It bundles SDL3 and SDL3_image 3.4.x for GPU shader
preview support.

## Building on macOS

Requires the Xcode Command Line Tools and SDL3 / SDL3_image from Homebrew.

Build a runnable `.app`:

```sh
cmake -B build
cmake --build build -j4
open build/src/kat5200.app
```

To open the project in the Xcode IDE for debugger or Instruments use, generate
the project on demand. The generated Xcode project is not committed.

```sh
cmake -G Xcode -B build-xcode
open build-xcode/kat5200.xcodeproj
```

Build a self-contained, relocatable `.app` plus compressed `.dmg`:

```sh
cmake --build build --target kat5200-macos-dmg
```

Output:

```text
build/dist/kat5200-<ver>-macos.dmg
build/dist/kat5200.app
```

The packaging target bundles the SDL3 dylibs and transitive dependencies into
`Contents/Frameworks`, rewrites load paths to `@rpath`, and re-signs ad-hoc.
Scripts:

- `cmake/package_macos_bundle.cmake`
- `cmake/make_icns.cmake`

The bundle is only ad-hoc signed. Apple Developer ID signing and notarization
remain manual steps before distributing off-machine. The packaging script stages
and signs in `$TMPDIR` to avoid the `com.apple.FinderInfo` attribute that
iCloud/FileProvider-synced folders force onto bundles, which `codesign` rejects.

## Building on Android

Toolchain:

- Android SDK with `compileSdk` 35
- NDK 27.3.13750724
- JDK 17
- Gradle

The APK supports Android phones and tablets, Android TV / Google TV, and Fire TV
devices. Native code is packaged for the `arm64-v8a`, `armeabi-v7a`, and
`x86_64` ABIs with `minSdk` 21. The `x86_64` ABI is mainly for Android emulator
images. Gradle drives the native build through the top-level `CMakeLists.txt`.
kat5200 builds as a shared library, `libkat5200.so`, loaded by the SDL activity.
Native rendering links `GLESv2` / `EGL`.

From `android-project/`:

```sh
cd android-project
./fetch-sdl-aars.sh
./gradlew assembleDebug
```

Use `assembleRelease` or `build` for other Gradle build variants.
Signed release APKs are written as
`app/build/outputs/apk/release/kat5200-<version>-release.apk`.

Gradle stages `kat5200.conf`, `profiles.zip`, and `shaders.zip` into
`app/src/main/assets` stored uncompressed. `profiles.zip` is zipped directly from
the existing `src/sql/dats/profiles.5200` and `src/sql/dats/profiles.8bit`
trees. It is not regenerated from DAT files during the Gradle build, so run the
profile-generation step below first if those trees are missing.

The same APK has both launcher and leanback launcher entries, so it appears on
phone/tablet launchers and Android TV home screens. ROM-set downloads use a JNI
`HttpURLConnection` backend over HTTPS only.

## Building the Profiles

Profiles are per-game TOML configuration files packaged into `profiles.zip`. The
old SQLite `kat5200.db3` is gone; the runtime reads TOML profiles directly.

Obtain TOSEC / No-Intro `.dat` files for the Atari 5200 and Atari 8-bit.

Generate the profile files with `dat2conf.pl`. The script writes the
`profiles.5200/` and `profiles.8bit/` trees into the current working directory,
and packaging expects them under `src/sql/dats`, so run it there:

```sh
cd src/sql/dats
perl dat2conf.pl <dat_file> [<dat_file2> ...]
```

This produces:

- CRC32-named TOML `.conf` files
- per-category CSV lists
- `list.csv` indexes

Package the trees into `profiles.zip`. `PROFILES_SRC` must point at the directory
that contains the two `profiles.*` trees.

```sh
cmake -D PROFILES_SRC=$PWD \
      -D OUTPUT_ZIP=$PWD/profiles.zip \
      -P <repo-root>/cmake/make_profiles_zip.cmake
```

The Linux install step runs this automatically. The archive is stored
uncompressed through 7-Zip when available, falling back to CMake's tar support.

## Building Shaders

The emulator ships precompiled GPU shader bundles under
`resources/shaders/bundles/<id>/`:

- SPIR-V for Vulkan
- Metal MSL
- Direct3D12 DXIL

kat5200 never compiles `.slang` source at runtime. The list of bundles to
distribute lives in `resources/shaders/distributed_bundles.txt`.

To rebuild bundles, use `tools/shader_bundles/rebuild_shader_bundles.py`. It
needs these host tools on `PATH`, plus a libretro `slang-shaders` checkout for
the upstream presets:

- `glslangValidator` or `glslc`, to compile GLSL to SPIR-V
- `shadercross`, the SDL3 variant, to cross-compile SPIR-V to MSL / DXIL
- `spirv-cross`, to reflect uniform and sampler metadata

Example full rebuild:

```sh
python3 tools/shader_bundles/rebuild_shader_bundles.py \
  --slang-shaders-dir /path/to/slang-shaders \
  --output-dir resources/shaders/bundles \
  --fixture-output-dir tests/shader_bundles \
  --work-dir build/shader_bundle_work \
  --glsl-to-spirv "$(command -v glslangValidator)" \
  --shadercross   "$(command -v shadercross)" \
  --spirv-cross   "$(command -v spirv-cross)"
```

Useful options:

- `--only <id>` rebuilds a single bundle.
- `--extra-bundle <id>=/path/to/preset.slangp` adds an external preset.

Each bundle gets:

- `bundle.toml` with pipeline metadata
- a `source/` copy
- `LICENSES.md`
- per-API compiled blobs

Bundles are staged into each platform package by
`cmake/stage_shader_bundles.cmake`.
