ZX Spectrum+ Interrupt-Driven Display Routine Explained
The Sinclair ZX Spectrum+ relied on a precise synchronization between its Z80 processor and custom ULA chip to generate video. This article details how the system utilized a 50Hz vertical blank interrupt to coordinate screen memory access, handle timing-critical tasks, and manage the contention between the CPU and video hardware.
Hardware Architecture and the ULA
At the heart of the ZX Spectrum+ video system was the Uncommitted Logic Array (ULA). Unlike modern computers with dedicated video RAM, the Spectrum shared its main memory between the CPU and the video circuitry. The ULA was responsible for generating the video signal in real-time by fetching pixel and attribute data directly from the same RAM used by the Z80 processor. This design required a strict timing protocol to ensure that the video output remained stable without flickering or tearing.
The 50Hz Vertical Synchronization Interrupt
The display routine was anchored by a hardware interrupt generated at the end of every video frame. In PAL regions, this occurred 50 times per second. When the ULA finished drawing the last line of the screen, it triggered an interrupt request (IRQ) to the Z80 CPU. This signal informed the processor that the vertical blanking period had begun, providing a safe window for the software to update screen data without interfering with the active display generation.
Memory Contention and Timing
Because the CPU and ULA shared the same memory bus, they could not access RAM simultaneously. During the visible screen area, the ULA had priority, frequently halting the CPU to fetch video data. This phenomenon, known as memory contention, reduced the effective speed of the processor during the display period. The interrupt-driven routine was essential because it allowed heavy processing tasks to be scheduled during the vertical blank or the border periods where memory contention was lower, ensuring smooth animation and responsive controls.
The Interrupt Service Routine
Upon receiving the interrupt signal, the CPU paused its current task and jumped to a specific memory address containing the Interrupt Service Routine (ISR). In the standard ROM, this routine handled essential housekeeping tasks such as scanning the keyboard matrix, flashing the border color, and incrementing the system frame counter. Programmers could hook into this interrupt to create custom display routines, allowing for split-screen effects, smooth scrolling, and precise music synchronization that matched the refresh rate of the television.
Software Coordination and Display Updates
While the ULA handled the physical drawing of pixels, the interrupt-driven software routine managed the logic of what was displayed. Game loops were typically synchronized to this 50Hz tick. By updating game logic and screen memory during the vertical blank interval triggered by the interrupt, developers ensured that changes to the display file occurred only when the ULA was not actively reading that portion of memory. This coordination prevented visual artifacts and maintained the stability of the interrupt-driven display system.