The ZX Spectrum Reverse Engineering and Clone Desgin Blog


A site dedicated to the reverse engineering of the ZX Spectrum and related projects.

< 26 of 68 >

Video Fetch Redesign

May 4, 2007

Philip Kendall (he of the Free Unix Spectrum Emulator) very kindly contacted me in response to the 'Memory to Display Interface' page to let me know that it is in fact the screen display byte that is fetched first, and not the attribute byte. This is of course extremely important if the ZX Spectrum floating bus behaviour is to be accurately reproduced.

This sent me on a new wave of research, in particular Ramsoft's website, where they give the floating bus quite an in depth analysis, and even provide a program you can run on the humble speccy to try this out for yourself.

The timings are a little unusual, but I think they take into account the 11 T-states consumed by the IN instruction used to sample the floating bus, which is why they are higher than the expected "first display byte T-state" of 14336.

My design (v1.4) reads an attribute and display byte pair one T-state in every four. However ramsoft suggest that it takes the Spectrum two T-states to read a pair, and it reads two pairs in quick succession - taking four T-states. By doing so it doesn't need to read anything else for the next four T-states.

This sounds really complicated as you have to fetch the byte pair for the next display location and store it before it is needed. My original design fetches and stores the attribute byte, followed by a display byte fetch, which it latches straight into the shift register at the same time as transferring the stored attribute byte into the output register.

To mirror the Spectrum we have to introduce a latch before the shift register to allow me to fetch the display byte and store it, fetch the attribute byte and store it (as now), and then transfer them together into the attribute output register and shift register - all in two T-states. This frees the input display and attribute registers, which can be loaded in the next two T-states with the next byte pairs.

In terms of the horizontal counter HC (clocked at 7MHz) the ZX Spectrum byte fetch scheme looks like this:

T-State HC3 HC2 HC1 HC0 Description
00000Display byte fetch
10010Attribute byte fetch
0011Output latch,
increment address
20100Display byte fetch
30110Attribute byte fetch
1011Output latch,
increment address

Examining this table we can see that a byte fetch occurs whenever HC0 goes from 0 to 1 and HC3 is low. The byte fetched will be a display byte if HC1 is low, an attribute if it is high.

The attribute and display bytes are transferred to the output registers when HC2 goes from low to high (we can use this rising edge at the end of the T-state). Memory contention with the Z80 should only occur during T-states 0 to 3 of every 8.

The output latch signal needs to be kept low for as short a time as possible. This is because the output shift register (74HC166) latches a new data byte at the next rising clock edge when PE is low. If PE is low for more than one clock cycle then the display byte will be latched multiple times and we will get a corrupted bitstream sent to the display.

If we just use HC2 as the latch enable then PE will be low for 4 clock cycles. To avoid this we should only consider HC2 when HC0-1 are high.

It is also extremely important that the attribute byte is loaded into the output register at exactly the same time that the display byte is loaded into the shift register. To do this we need to synchronise the rising edge of the latch enable signal with the rising edge of the pixel (7MHz) clock. As the latch enable is low for a complete pixel clock cycle, we can synchronise the rising edges by ORing the latch enable with the pixel clock.

As the time spent between the byte fetch start and the first output latch is 2 T-states, we need to delay Vout by 4 pixel clock cycles instead of the two currently. Now I'm glad I used an octal D-Type latch for the delay instead of a straight D-Type flip flop!

The modifications to the horizontal sync circuit and the video memory circuit to implement this new fetch strategy are shown in schematics version 1.5.