# Changelog

## 10.0 (2026-04-04)

- Dropped support for Python 3.9

- Added the `--ay` option to trace.py (for capturing AY audio when writing a WAV file)

- Added the `ay` parameter to the #AUDIO macro (to set whether AY audio is captured)

- Added the `--beeper` option to trace.py (for capturing beeper audio as well when `--ay` is specified)

- Added the `bpr` parameter to the #AUDIO macro (to set whether beeper audio is captured along with AY audio)

- Added support for the MEMPTR register to CMIOSimulator and CCMIOSimulator

- Added the `memptr` parameter to the #SIM macro (to set the MEMPTR register)

- snapinfo.py now shows the MEMPTR register value in SZX snapshots

- Added support to trace.py for setting the MEMPTR register before execution begins, for reading and writing MEMPTR in SZX snapshots, and for tracing its value via the `r[memptr]` replacement field in the `TraceLine*` configuration parameters

- Added support to tap2sna.py for setting the MEMPTR register in SZX snapshots, and for tracing its value via the `r[memptr]` replacement field in the `TraceLine` configuration parameter

- Added support to bin2sna.py and snapmod.py for setting the MEMPTR register in SZX snapshots

- Added the `TraceHeader` and `TraceHeader2` configuration parameters for trace.py (to specify headers to print before a trace)

- Added support to the #AUDIO macro for keyword arguments

- Added support to rzxplay.py for ignoring any snapshots after the first one (which is useful for playing some RZX files created by the Fuse emulator)

- Added a border area to the screen displayed by rzxplay.py and trace.py

- Updated the comments generated for ‘IN r,(C)’ immediately after ‘LD BC,$XXFE’ and ‘IN A,($FE)’ immediately after ‘LD A,n’ when a single half-row of the keyboard is read

- Updated the default values of `ContentionBegin`, `ContentionEnd` and `InterruptDelay` in the [AudioWriter] section

- Added support for multiple values to the `InterruptDelay` parameter in the [AudioWriter] section

- Fixed the bug in CSimulator that restricts the `timeout` simulated load configuration parameter to a maximum value of 1227 seconds

- Fixed how tap2sna.py handles zero-length pulses in the encodings of 0s and 1s in a PZX DATA block

## 9.6 (2025-05-12)

- tap2sna.py can now load from two tape files (e.g. when side 1 and side 2 of a tape are in separate files)

- Added the `--press` option to tap2sna.py (for pausing the tape and simulating keypresses before resuming)

- Added the `--tape-skip` option to tap2sna.py (for skipping one or more blocks on a tape)

- Added support to the `--ram` option of tap2sna.py for the `patch` operation (for applying a binary patch file)

- Changed the default value of the `accelerate-dec-a` simulated LOAD configuration parameter for tap2sna.py from `1` to `3`

- Added the `activision`, `alternative3`, `audiogenic-0`, `audiogenic-1`, `codemasters`, `diver`, `gremlin2-0`, `gremlin2-1`, `kwc-0`, `kwc-1`, `mirrorsoft2` and `operasoft` tape-sampling loop accelerators

- Removed the `dinaload`, `gremlin2`, `housenka`, `suzy-soft` and `suzy-soft2` tape-sampling loop accelerators

- Added the `Screen` configuration parameter for trace.py (to specify whether to display screen contents)

- Added the RST handler component

- Added the `--handle-rst` option to sna2ctl.py and sna2skool.py (for activating the RST handler)

- Added the `HandleRST` configuration parameter for sna2ctl.py and sna2skool.py (to activate the RST handler)

- Fixed how tap2sna.py handles `--tape-stop` for PZX files that contain STOP blocks

- Fixed the bug that prevents the `m` replacement field from being used in the `TraceLine` configuration parameter when tap2sna.py runs a custom LOAD command

## 9.5 (2025-01-28)

- Dropped support for Python 3.8

- Added the comment generator component

- Added the `--comments` option to sna2ctl.py and sna2skool.py (for generating instruction comments)

- Added the `Comments` configuration parameter for sna2ctl.py and sna2skool.py (to enable instruction comment generation)

- trace.py now responds to keypresses while running with screen contents displayed

- Added the `--map` option to trace.py (for writing a code execution map file)

- Added the `UserAgent` configuration parameter for tap2sna.py (to specify the User-Agent header in HTTP/HTTPS requests)

- Added support to the #CALL macro for calling an arbitrary function

- Added the `--patch` option to snapmod.py (for applying a binary patch file)

- The #REG macro now always renders the IXh, IXl, IYh and IYl registers with a lower case ‘h’ or ‘l’

- Added the #FRAMES macro (as an alternative to the `#UDGARRAY*` macro, which is now deprecated)

- Made the audio writer a pluggable component

- Made the code map reader a pluggable component

- Improved handling of TC2048, TC2068 and TS2068 Z80 snapshots

- Fixed how trace.py builds a PNG image in 128K mode

- Fixed the bug that prevents skool2asm.py, skool2bin.py and skool2html.py from handling an instruction that crosses the 64K boundary

- Fixed how BIN expressions are evaluated in BASIC listings

## 9.4 (2024-10-05)

- Added support to skool2bin.py for reading configuration from skoolkit.ini

- Added the `--ini` and `--show-config` options to skool2bin.py (for setting the value of a configuration parameter and for showing all configuration parameter values)

- Added support to skool2bin.py for padding the output with zeroes (as specified by the `PadLeft` and `PadRight` configuration parameters)

- Added the `--screen` option to trace.py (for displaying screen contents while running)

- Added the `ScreenFps` and `ScreenScale` configuration parameters for trace.py (to specify the frame rate and scale factor when displaying screen contents)

- Added support to trace.py for writing a PNG file after code execution has completed

- Added the `PNGScale` configuration parameter for trace.py (to specify the scale factor of the PNG image)

- Added support to trace.py for multiple output file arguments

- snapinfo.py now shows AY register values in 128K SZX and Z80 snapshots and the last value written to port $FE in SZX snapshots

- Added support to the #FOREACH macro for the `POKEname` special variable

- Added support to the #LET macro for setting individual key-value pairs in dictionary variables

- Added the `Download` parameter to the [Game] section (for specifying a download message/link to appear in the footer of every page)

- Added the `LinkInternalOperandsMinDistance` parameter to the [Game] section (for avoiding hyperlinks to nearby instructions)

- Fixed how ADC and SBC instructions affect the half-carry flag

- Fixed how ‘BIT n,(IX/Y+d)’ affects bits 3 and 5 of the flags in the C version of the Z80 simulator

- Fixed how IX/IY offset addresses are calculated in the C version of the Z80 simulator

## 9.3 (2024-08-10)

- Added support to tapinfo.py and tap2sna.py for reading PZX files

- Added support to bin2tap.py for writing PZX files

- Added support to tap2sna.py for the `m` (memory) replacement field in the `TraceLine` configuration parameter

- Added support to trace.py for the `m` (memory) replacement field in the `TraceLine*` configuration parameters

- Added the `--state` option to trace.py (for setting hardware state attributes before code execution begins)

- Added support to trace.py for writing a WAV file after code execution has completed

- Added the `Opcodes` configuration parameter to sna2skool.py (for specifying additional opcode sequences to disassemble)

- Added the @bytes directive (for specifying the byte values to which an instruction should assemble)

- Added the `--tape-start` and `--tape-stop` options to tapinfo.py (for specifying the block numbers at which to start or stop showing info)

- tapinfo.py now shows info for TZX block types 0x18 (CSW recording) and 0x2B (set signal level), and also recognises the deprecated TZX block types 0x16, 0x17, 0x34 and 0x40

- The `--find`, `--find-text` and `--find-tile` options of snapinfo.py now search all RAM banks in a 128K snapshot by default

- Added support for path ID replacement fields in the `destDir` parameter of items in the [Resources] section

- Fixed the bug that prevents the `--reg` option of trace.py from accepting hexadecimal values prefixed by ‘0x’

## 9.2 (2024-05-11)

- Added a Z80 instruction set simulator implemented in C (as a faster alternative to the pure Python Z80 simulator)

- Added the rzxplay.py command (for playing an RZX file)

- Added the rzxinfo.py command (for showing the blocks in or extracting the snapshots from an RZX file)

- Added support to sna2ctl.py for reading code execution maps produced by rzxplay.py

- Added support to tap2sna.py for TZX block type 0x15 (direct recording)

- tapinfo.py now shows info for TZX block type 0x15 (direct recording)

- Added support to trace.py for executing machine code in +2 snapshots

- Added the `python` simulated LOAD configuration parameter to tap2sna.py (for forcing usage of the pure Python Z80 simulator even if the C version is available)

- Added the `--python` option to trace.py (for forcing usage of the pure Python Z80 simulator even if the C version is available)

- Fixed the lazy evaluation bug that can make the #FONT, #SCR and #UDG macros create frames with incorrect graphic content

- Fixed the bug that can make trace.py stop too soon when the `--max-tstates` option is used

- Fixed the contention pattern for the OUTI/OUTD/OTIR/OTDR instructions

## 9.1 (2024-02-03)

- Added support to snapmod.py for modifying SZX snapshots and 128K snapshots

- Added support to bin2sna.py for writing 128K snapshots (by using the `--page` and `--bank` options, or by providing a 128K input file)

- Added support to bin2tap.py for writing 128K TAP files (by using the `--7ffd`, `--banks` and `--loader` options)

- Added support to bin2sna.py, snapmod.py, tap2sna.py and trace.py for modifying 128K RAM banks (via the `--move`, `--poke`, `--ram move` and `--ram poke` options)

- Added the #BANK macro (for switching the RAM bank that is mapped to 49152-65535)

- Added the @bank directive (for specifying the RAM bank that is mapped to 49152-65535, and for populating a RAM bank from the contents of another skool file)

- Added the `--banks` option to skool2bin.py (for processing @bank directives and writing RAM banks 0-7 to a 128K file)

- Added the `cmio` simulated LOAD configuration parameter to tap2sna.py (to specify whether to simulate memory and I/O contention)

- Added the `--cmio` option to trace.py (to enable simulation of memory and I/O contention)

- Added the `cmio` parameter to the #AUDIO, #SIM and #TSTATES macros (to specify whether to simulate memory and I/O contention)

- Added the `execint` parameter to the #AUDIO, #SIM and #TSTATES macros (to specify whether to simulate the execution of interrupt routines)

- Added the `tstates` parameter to the #SIM macro (to set the value of the simulator’s clock)

- Added the `iff` parameter to the #SIM macro (to set whether interrupts are enabled)

- Added the `im` parameter to the #SIM macro (to set the interrupt mode)

- Made the `stop` parameter of the #SIM macro optional

- Added support to the #AUDIO, #SIM and #TSTATES macros for executing code in a 128K memory snapshot

- Fixed how trace.py handles the value of the SP register in a 128K SNA file

- Fixed how tap2sna.py and trace.py log timestamps when an interrupt occurs

- Fixed how interrupts are accepted when tap2sna.py and trace.py execute code in a simulator

- Fixed how the Z80 instruction set simulator updates bit 2 of the flags register when executing an ‘LD A,I’ or ‘LD A,R’ instruction just before an interrupt is accepted

- Fixed the bug that makes the `--basic` option of snapinfo.py fail when the value of PROG is 65535

- Fixed the bug that prevents an M directive from being repeated in a control file loop

## 9.0 (2023-11-04)

- Dropped support for Python 3.7

- tap2sna.py now performs a simulated LOAD by default, and will also overwrite an existing snapshot by default

- Added the `machine` simulated LOAD configuration parameter to tap2sna.py (to specify whether to simulate a 48K or a 128K Spectrum)

- Added the `load` simulated LOAD configuration parameter to tap2sna.py (to specify an alternative command line to use to load the tape)

- Added the `polarity` simulated LOAD configuration parameter to tap2sna.py (to specify the EAR bit reading produced by the first pulse on the tape)

- Added the `in-flags` simulated LOAD configuration parameter to tap2sna.py (to specify how to handle ‘IN’ instructions)

- The output snapshot argument of tap2sna.py is now optional

- Added the `DefaultSnapshotFormat` configuration parameter for tap2sna.py (to specify the default output snapshot format)

- Added support to tap2sna.py for register pairs (`r[bc]`, `r[de]` etc.) in the `TraceLine` configuration parameter

- Added the `antirom`, `ernieware` and `housenka` tape-sampling loop accelerators

- Statistics for ‘DEC A’ tape-sampling delay loops are now shown by tap2sna.py when `accelerator=list`

- Added support to trace.py for executing machine code in 128K snapshots

- Added support to trace.py for reading configuration from skoolkit.ini

- Added the `--ini` and `--show-config` options to trace.py (for setting the value of a configuration parameter and for showing all configuration parameter values)

- Added the `--no-interrupts` option to trace.py (to prevent the execution of interrupt routines, which are now executed by default)

- Added support to bin2sna.py, tap2sna.py and trace.py for writing SZX snapshots

- Added support to bin2sna.py and tap2sna.py for setting the `fe` hardware state attribute (i.e. the last value written to port 0xFE in SZX snapshots)

- Added support to the #AUDIO macro for passing delays through a moving average filter (which can produce higher quality audio, especially for multi-channel tunes)

- Added support to control directive loops for avoiding repetition of an `N` directive at the start of a loop

- tapinfo.py now shows the LINE number (if present) for ‘Program:’ header blocks, and renders BASIC tokens in header block names

- snapinfo.py now shows the current AY register in 128K SZX and Z80 snapshots

- Changed the default value of `H` and `A` for the @assemble directive to 2

- Fixed the bug that prevents tap2sna.py from loading a tape that has a hash character (`#`) in its filename

## Older versions

- SkoolKit 8.x changelog
- SkoolKit 7.x changelog
- SkoolKit 6.x changelog
- SkoolKit 5.x changelog
- SkoolKit 4.x changelog
- SkoolKit 3.x changelog
- SkoolKit 2.x changelog
- SkoolKit 1.x changelog