< all news

Copperline 0.16.0: one-command WHDLoad, a game library, and a new Amiga game built on Copperline

This is the release where the machine meets the people who make and play its software. A WHDLoad-installed game now boots straight from its archive - copperline --whdload Turrican.lha and nothing else - and the launcher grows a proper game library around that, with details and cover art fetched from OpenRetro. On the other side of the same coin, --run warp-boots a freshly built Amiga executable from the host filesystem for people writing new Amiga software - and several of this cycle's accuracy fixes came out of exactly that use, because a studio is building a new commercial Amiga game with Copperline on the desk beside real AGA hardware.

Storage grows a built-in lide.device-compatible IDE board with ATAPI CD-ROM support, OFS directory mounts that boot Kickstart 1.3, a Create Image workshop for fresh ADFs and HDFs, and gzip-compressed hardfiles. Around the machine: configurable output paths with an opt-in portable mode, Kickstart ROM identification by checksum, an on-screen keyboard and picture centring on the desktop, bezel sticker decals, and IPF images in the browser build. As always it is a hardware-behaviour release: compatibility fixes model the underlying Amiga subsystems rather than individual titles.

A new Amiga game is being built on Copperline

Brazen Gameplay are developing Urb-X Warriors: The Lost City, a brand-new commercial 16-bit Amiga game, and they are using Copperline as part of their development workflow - running work-in-progress builds in the emulator right beside real AGA hardware. That is exactly the kind of use an emulator dreams of: a game studio pushes the machine in ways thirty-year-old software never will, and they notice everything.

My favourite find of the cycle came from them. Their code read back a write-only chip register and OR-ed the result into palette writes. On real AGA hardware the chip data bus floats, so the read returns whatever residue the last driven bus cycle left behind - and the palette went dark. Copperline, like other emulators, returned a clean zero, so the bug hid. As of 0.16.0 Copperline models the floating bus, and the same code misbehaves in the emulator exactly as it does on the real silicon. An emulator being right sometimes means faithfully reproducing your bugs - that is what makes it a development tool you can trust.

The same collaboration drove the fix that makes Agnus bitplane pointers one live counter, the fix that places AGA's first 64-pixel wide-fetch gulp on the absolute grid, and a guarantee that pausing a session to inspect the machine never changes what the machine goes on to do. If a new commercial Amiga platformer sounds like your kind of thing, their Kickstarter page is the place to follow it.

Direct WHDLoad boot

copperline --whdload game.lha boots a WHDLoad-installed game package directly - no Workbench disk, no hand-built hard drive. The package is extracted once into a per-game library so savegames persist on the host, a boot volume is regenerated around the real WHDLoad program on every launch, and the machine is derived from the slave header - the canonical A1200 with 8 MB of fast RAM unless your config says otherwise.

Kickstart images are identified by content using the same CRC WHDLoad itself uses, so byte-swapped dumps, doubled images and Cloanto-encrypted ROMs are all recognised, and a slave demanding a missing image fails naming the exact file it wants. The WHDLoad and skick support archives are fetched with pinned checksums at packaging time; the Kickstart ROMs remain yours to supply, as ever.

A game library

The launcher's WHDLoad page grows into a browsable collection: point it at a folder of games as .lha, .zip or plain directories, and it lists them with details and cover art from OpenRetro, A-Z shortcuts to jump the list, and drag-and-drop of a package onto a running machine to reboot into it. Contributed by Lee Hobson (@hobbo91).

--run: a developer warp launch

copperline --run build/hello stages a minimal boot volume, mounts the executable's directory live, and warp-boots until the guest OS loads the program - about one wall-clock second to reach your code on the bundled AROS ROM, in the spirit of the vscode-amiga-debug workflow. With --gdb the session stops at the program's first instruction, and the control protocol gains a loadseg breakpoint kind for scripted sessions. It composes with every headless flag, so a CI run can build an Amiga binary and screenshot it running. If you have ever wanted to write Amiga software with a modern edit-compile-run loop, this release is for you.

A lide.device IDE board, and ATAPI everywhere

A new built-in Zorro II IDE board is compatible with LIV2's open-source lide.device (RIPPLE, RIDE and AT-Bus 2008 personalities). On top of it, ATAPI CD-ROM support arrives across all three IDE surfaces - Gayle, the A4000's motherboard port and the new board - so a .cue / .iso / .chd path on any IDE drive slot attaches a real IDE CD-ROM drive, and [[host_disk]] can hand a real host disk to a lide channel. Contributed by Simon Dick (@sidick).

OFS mounts that boot Kickstart 1.3

A hard-drive slot pointing at a host directory can now build its volume as OFS (filesystem = "ofs") - the filesystem every Kickstart ROM since 1.2 carries - so a directory mount boots a genuine 1.3 machine to Workbench with no FFS handler installed anywhere. Contributed by Simon Dick.

A Create Image workshop

Storage > Create Image... makes fresh disk images from inside the launcher: DD or HD floppies, standard or extended ADF, any of the eight DOS types, boot code and a volume name; hard-disk images up to 9999 MB or GB with or without an RDB, custom geometry, boot priority and sparse allocation. Contributed by Lee Hobson.

Configurable paths, portable mode and a default config

Everything Copperline produces - screenshots, save states, video and input recordings, NVRAM, traces, waveform captures - now lands in named folders under the host-data directory instead of the process working directory, and a new [paths] section, with its own launcher page, names where each kind of output goes (plus where empty file dialogs open). Relative entries follow a movable base, and a portable.txt next to the executable makes the whole installation self-contained, saves and all - an emulator on a USB stick. The launcher's Save button now offers Save As / Save default / Reset default, and a saved default is what Copperline starts with when nothing else names a config. Contributed by Lee Hobson.

Kickstart ROMs, identified by checksum

A ROM file's name is whatever its dumper called it; Copperline now says which Kickstart it actually is - 67 known images from 1.0 to 3.2.3, betas, prototypes and the CD32 / CDTV extended ROMs included - in the startup banner, the About panel, the ROM-load OSD and the launcher's ROM tab.

The desktop, the bezels and the browser

The A600 keyboard strip from the browser build arrives in the desktop window with a status-bar toggle, and new H / V-centre controls nudge the TV picture the way a monitor's front-panel knobs did. The 1084 front is rebuilt against fresh reference photography - much closer to the real thing, contributed by Lee Hobson - the tube now shows the whole captured raster, and a bezel stickers folder puts your own decals on the case, the same on desktop and web alike.

copperline.dev/try now reads IPF images, offers both monitor fronts, and untangles Esc from fullscreen with the Keyboard Lock API - tap Esc to release the mouse, hold it to leave fullscreen.

Storage and capture odds

  • Gzip-compressed hardfiles (.hdz) open directly, with session-only writes.
  • DMS archives with non-linear track layouts extract correctly.
  • The launcher's Storage Browse dialog picks directories, and serial TCP addresses are typed straight into the I/O Ports tab.
  • --screenshot-after and --save-state-after now repeat, so one run can capture a whole sequence.

Hardware accuracy fixes

  • Agnus bitplane pointers are one live counter: never reloaded at vertical blank, and a CPU half-write merges into the DMA-advanced live value - the behaviour a display that rewrites its pointers mid-frame depends on.
  • An AGA display fetching 64 pixels per gulp is placed from the absolute wide-fetch grid, so the first gulp sits left of the display window instead of leaking a seam onto it.
  • Reading a write-only custom register returns the residue of the last driven chip-bus cycle, not a clean zero - the floating-bus behaviour reported from real AGA hardware by Brazen Gameplay.
  • CPU palette writes resolve against the live BPLCON3 bank, and an out-of-range playfield priority blanks the playfield on Denise only, matching photographed real-chip behaviour - the Bubble and Squeak and Alfred Chicken in-game graphics.
  • Each ATA device keeps its own cylinder registers, as on real hardware where the signature a driver probes belongs to the selected device.
  • Cold-boot RAM contents are configurable - zero, seeded random or a fixed 16-bit pattern - for software whose behaviour depends on what a real machine's DRAM woke up holding.
  • Host volume names are converted to the Amiga's own Latin-1 character set, so an accented label survives the trip into AmigaDOS (Volker Schwaberow).

Desktop, tooling and platform

  • Stopping a session at an exact time through the control protocol no longer perturbs the timeline: a single run_until and the same span sampled in ten stops now end on the identical cycle, so an investigation can add observation points without changing what it observes.
  • Opening the debugger or another tool window leaves main-window Amiga input alive.
  • A trapping WASM plugin board is isolated permanently instead of re-trapping every frame, and its DMA commits transactionally; a two-level case-insensitive path cache speeds up directory-mounted volumes (both Volker Schwaberow).
  • Debugger fixes: the memory-scan address is masked to the bus width, and copper-list disassembly aligns to the list start (Volker Schwaberow).
  • HostSocket's bsdsocket.library LVO table extends through the real end of the jump table, so software indexing deep LVOs finds them (Simon Dick).
  • The dependency tree moves to current releases, and the m68k core at 0.10.14 fixes a real 68000 MOVEM.L bus-order bug that corrupted lide.device sector reads under real Kickstart.
  • Homebrew installs from the release archive again (the 0.15.0 formula needed a fix).

Contributed this cycle

Copperline welcomes a new contributor this cycle: Volker Schwaberow (@vschwaberow), who arrived with five merged PRs - WasmBoard fault isolation and transactional DMA, the host-filesystem path cache, two debugger fixes, Latin-1 volume labels and a disassembler cleanup. Welcome aboard.

Lee Hobson (@hobbo91) again wrote more code this cycle than I did - 24,000 lines to my 16,000; I have made my peace with it. His cycle: the WHDLoad game library with OpenRetro details and cover art plus its A-Z navigation, the Create Image workshop, the configurable-paths system with portable mode and the saved default config, and the rebuilt 1084 bezel.

Simon Dick (@sidick) contributed the lide.device-compatible IDE board with ATAPI CD-ROM and host-disk support, OFS for directory-mounted hard drives, the launcher's directory picker, and the full-length bsdsocket LVO table.

And Brazen Gameplay fed back findings from running their work-in-progress game on Copperline beside real AGA hardware - the floating-bus model, the bitplane-pointer fix, the wide-fetch origin fix and the deterministic control stepping all trace to that collaboration. Four people shipped 201 commits in seven days. This project has become a team, and it is wonderful to watch.

Compatibility notes

Save states from 0.15.0 do not load in 0.16.0. The serialized machine shape changed several times this cycle, so the state format version moves from 50 to 54. Re-create snapshots after upgrading.

Output files move out of the working directory. Screenshots, save states, recordings, NVRAM, traces and waveform captures now land in named folders under the host-data directory, or wherever [paths] points. Explicit CLI paths (--screenshot-after and friends) are still used exactly as written, and legacy battmem.nvram / cd32-nvram.bin files in the working directory keep being used from there - real game saves are never silently relocated.

A saved default configuration now auto-loads. A default saved from the launcher is what Copperline starts with when neither --config nor ./copperline.toml names one. For reproducible runs on a machine you do not control, pass --factory to ignore it.

Get it

Builds for macOS, Linux and Windows are on the release page, and the Homebrew tap is updated. Or skip the download entirely: copperline.dev/try is the same emulator.

Copperline also has a Patreon. Nothing there buys a feature or a place in the queue - monthly support goes towards development time, real hardware to measure the emulator against, and the code-signing subscriptions that would let the downloads open without a warning.

- Andrew Hutchings (LinuxJedi) · linuxjedi.co.uk