32

I've roughly known the concept for years, but never really understood it. Back in the day, two types of RAM typically used in home computers: static and dynamic RAM. Static RAM (SRAM) was apparently easier to use because it didn't require refreshing (and circuitry to go along with that), and Dynamic RAM (DRAM) was cheaper but required the RAM to be "refreshed".

So as I understand the story, Woz designed the Apple II to use DRAM because it was cheaper but was able to avoid designing refresh circuitry because he used the odd-phase of the 6502 to do it for him by reading the next chunk of video memory which would effectively do the refresh.

So this leaves two questions in my mind:

  1. What exactly is DRAM refresh? Is it simply making sure a memory cell is accessed which gives it an electrical charge to keep it alive, or is it more like a 'read and re-write'?

  2. If this refresh mechanism is the reason for the non-linear memory layout of the Apple II video, then why? Is it because the gap of 64 lines was the amount of time that the even-phase would get for compute while the video circuitry was still displaying progressively?

For what its worth, how many chips did Woz actually save by doing this anyway?

1

3 Answers 3

33

Summary

Each DRAM chip has multiple "rows" of memory, and each row needs to be accessed in a certain way (not necessarily via a read or write) on a regular basis in order to avoid the memory "fading away." (Basically, this access recharges the capacitors from which the DRAM row is made.)

The Apple II uses two tricks to do this refresh.

  1. Any read or write of a single row will refresh that row; on such a read/write the Apple II generates some additional signals that refresh the rows in all the other RAM chips that are not being read/written.
  2. While the CPU is not using the bus, the video system reads through an area of RAM to get the data for the screen. This generates reads from a sufficient number of locations with sufficient frequency that, in combination with #1 above, all RAM is guaranteed to be accessed often enough that it will stay refreshed.

The refresh mechanism is entirely unrelated to the non-linear layout of the video system data; it would work just as well if the layout were linear. The non-linear scanning of video memory does save some circuitry in the address generation of the video system itself, however, so Woz took advantage of the fact that the the refresh system doesn't care in what order the addresses are accessed, so long as they are all accessed within a given amount of time.

The following goes into more detail, but it's still more of an overview than a full and complete description. Once you understand the basic concepts you should be able more easily to understand the detailed documentation such as the data sheets linked below and the schematics, as well as be able to ask more precise questions here for particular details.

Chip Select

To start with, you need to understand that static RAM chips (and other peripheral chips) have a "chip select" (CS) pin that, when asserted, tells the chip to read the address bus and read data from or write data to the data bus. (There may be more than one CS pin, but they all need to be asserted together.) So the normal sequence for a read from such a device is to put the desired address on the address bus and then assert CS for just that chip (making sure all other chips have CS deasserted to avoid conflicts), causing it to output the requested data on the data bus.

DRAM Chip Select

The Mostek MK 4116 and similar DRAM used in the Apple II and many other '70s and '80s computers works slightly differently: there are two select lines: row address select (RAS) and column address select (CAS). Among other things, this allowed the chip to have fewer pins since the low-order bits of the address would be sent separately from the high-order bits, using the same pins for both. Thus a read cycle for DRAM is a bit more complex. As shown at the top of page 5 of the data sheet linked above, it is:

  1. Put the desired address on address bus.
  2. Configure your DRAM address logic to send the lower order bits of the address bus to the DRAM chips' address lines.
  3. Assert RAS for all of the DRAM the chips, and then wait a bit for them to read those lower-order bits.
  4. Reconfigure your DRAM address logic now to send the higher order bits of the address bus to the DRAM chips' address lines.
  5. Assert CAS only for the appropriate bank of DRAM (eight chips, each on one line of the data bus) and then wait a bit for the DRAMs to read those higher-order address bits, read the data from RAM, and start driving the data bus with the data they read.
  6. Read the data from the data bus and then deassert RAS and CAS, which will deselect the chips in the bank so that they stop driving the data bus.

There are a couple of important things to note here. First is we assert RAS to all of the DRAM chips. This doesn't cause conflicts because RAS doesn't cause DRAMs to drive the data bus, it just causes them to read the row address from the address bus. Second is that we assert CAS only to one bank: because CAS is what causes the DRAMS to send their data out on the data bus, we must not enable CAS for more than one bank or there would be a conflict.

DRAM Refresh

A DRAM read of any address from a row automatically does a refresh of that entire row. But it's actually a bit easier than that: on the 4116 you don't actually need to do a full read, you need only assert RAS and that's enough to refresh the row. So even a chip that never has CAS asserted after RAS, and thus doesn't actually select a column from that row and drive the data bus with its value, will still have that entire row refreshed. So as long as you're regularly accessing all of the rows with RAS, even if you don't eventually read the data, the DRAM will be refreshed. (The timing diagram that shows this is on the bottom of page 6 of the data sheet linked above.)

Page 148 of the January 1978 Apple II Reference Manual gives an overview of how the DRAMs are connected, though it can also help to consult this Apple II schematic to confirm particular details. While the CAS line is enabled separately for each DRAM bank (which it must be to avoid bus conflicts on DRAM data output), the address pins and RAS are wired in common for all the DRAM banks. This means that an access to any single RAM location will generate an RAS select for that row on all the DRAM chips, refereshing that row in all of them.

Since the DRAM row addresses are 7 bits wide, this means that so long as within the period needed for DRAM refresh you access (for read or write) 128 different RAM locations that differ in their seven lowest-order address bits, you will referesh all of the DRAM on the system. These locations could be,

  • $00-$7F,
  • $B800-$B8FF,
  • $0000, $0081, $0102, $0183, $0204, ..., $3F7F,
  • or any other combination.

Video System RAM Access

Now the CPU may or may not access all of the rows regularly; it depends on the program being run. But in the Apple II the CPU is using the address and data buses only half the time: when the Φ2 ("phi two") clock signal is high. The other half of the time, when Φ2 is low, it's doing internal operations and not using the address or data buses.

This other time, when the inverse clock Φ1 is high, is when the video system accesses RAM to read the screen areas for the data to generate the video display. The processor and video system continually alternate cycles this way, CPU on Φ2 and video system on Φ1. This is shown in the diagram from Woz's Apple II system description in the May 1977 issue of BYTE:

Apple II display generator block diagram

The video system, during its cycles, simply walks through each address in the screen memory, reading it and then using that data to generate part of the scan line on the video monitor or TV. And now you see why the Apple II uses the rows, and not the columns, for the low-order address bits: this means that the video system will be looping through every row in each DRAM in every bank, asserting RAS, as the preparation for asserting CAS in the bank from which it's reading the screen information. This loop happens fast enough that, as a side effect, it refreshes all the RAM in the system.

Since this all happens during Φ1, when the CPU is off the bus, the CPU neither knows nor cares that this is happening. Thus it's often called "transparent refresh."

Apple II Video RAM Layout

There are two unusual things about the Apple II video RAM. First, in high-res graphics the lines as displayed on the screen are not sequential in memory: the second "row" of memory is actually displayed a third of the way down the screen, the third "row" two-thirds down, and then the fourth "row" of memory is the second line on the screen. Second, for both high-res graphics and text/low-res graphics, there are some "holes" between the memory "rows" that are bytes that do not generate anything on the display.

Neither of these has anything to do with refresh or even the logic to handle RAS, CAS and DRAM address multiplexing. The former just saves a couple of chips in the video system's memory access logic, and the latter is related to making it easier to get the right timing for the scan lines that are being generated from the data in screen memory.

(Actually, the above paragraph may be wrong about the layout not affecting the DRAM refresh; see Supercat's comments below, and this question.)

7
  • Remember also that the Apple II had to make the refresh sequence and memory layout work in both "high res" and "low res" modes, which occupied different areas of the address space and would cause the scanout to hit different amounts of memory. That in itself may explain some things about the weirdness.
    – Chromatix
    Commented Mar 3, 2020 at 15:16
  • @Chromatix It matters not where the frame buffer is, so long as it has at least 128 bytes covering every combination of the 7 low-order bits. (The smallest, text/low-res graphics, is 1 KB in size and contiguous.) Thus, video mode does not matter. I've expanded the "DRAM Refresh" section of my answer to cover this and give references.
    – cjs
    Commented Mar 4, 2020 at 2:47
  • 1
    @cjs: It's important that the row address be unaffected by video mode unless one ensures that mode switches only occur at certain "safe" time. Otherwise repeated mode switches could cause some rows to get starved.
    – supercat
    Commented Mar 6, 2020 at 1:28
  • @supercat Sure, but the question here is not, "is there some video memory arrangement that could be made that would break this refresh system," but "would the refresh system need to be changed at all were the video addressing linear, rather than broken up the way it is." The answer to that is "no." So clearly the frame buffer layout was not in response to refresh concerns because it didn't change any of the refresh concerns.
    – cjs
    Commented Mar 6, 2020 at 2:27
  • @cjs: If hires mode was linear, that would tend to imply that some of the column bits would be controlled by different parts of the counter in different modes, which would in turn make it possible to corrupt the refresh sequence by changing modes at interesting times. Perhaps it would be possible to make text mode simply advance the counter more slowly than graphics mode, in which case switching between modes mid-screen would yield a garbled display but still result in a reasonable refresh sequence, but trying to do something like the split modes would be more difficult.
    – supercat
    Commented Mar 6, 2020 at 5:39
26

DRAM requires that each row of the memory is read and re-written regularly, at least every few milliseconds for the devices available at the time the Apple II was designed. This contrasts with the 16ms (NTSC) or 20ms (PAL) per video field, so several complete DRAM refreshes are required per video frame.

This is made much easier by the DRAM chip having a row buffer which is filled with the contents of the row every time the /RAS strobe is triggered, and written back when it is released. So it is only necessary for the computer to arrange for some address in each row to be accessed (either read or write), which involves both a /RAS and /CAS strobe to provide a row and column address, or for a special /RAS-only refresh cycle.

Some CPUs like the Z80 include specialised DRAM handling circuitry which produces refresh cycles automatically, and multiplexes the row and column addresses in a way that's convenient for accessing DRAM. This however means that some CPU cycles are "lost" to the refresh process, and that the CPU has to be informed when DMA accesses occur so that it can get out of the way by pausing. It also makes interfacing the CPU to SRAM more difficult.

The 6502, used by the Apple II, has a much more straightforward bus interface, in which addresses are provided throughout the cycle but data transfer occurs only during the second half. Many 6502 computers take advantage of this to interleave video scanout accesses with CPU accesses, so that no CPU time is lost to them. It was also reasonably common practice to rely on the video scanout to perform the DRAM refresh function, both so that no dedicated refresh hardware had to be added, and so that no cycles were consumed by it. Typically the 6845 CRTC (or a clone thereof) was used to generate the scanout addresses and video timing.

To achieve this, the video memory has to be laid out so that every frame refresh touches all of the DRAM rows. Assuming the screen refresh rate is at least as fast as the required refresh interval of the DRAM, this is sufficient. Some computers, including the BBC Micro, took special measures in their address translation (from linear on the bus to row/column multiplexed format to the DRAM) to ensure that every possible screen configuration would meet this requirement. In the case of the BBC Micro, the Teletext mode which used only 1000 bytes of RAM was the critical design factor, but the circuitry was designed to present a logically linear address space to the CPU regardless of any contortions behind the scenes.

It appears that in the Apple II, more of these contortions are left visible to the CPU in terms of the layout of video memory. This probably saved a little bit of hardware in the DRAM address multiplexer, and may have been influenced by the higher refresh rate needed in the original Apple II's DRAM than in the later devices available for the BBC Micro. You could get some idea of the magnitude of the saving by comparing the schematics of the original BBC Micro and original Apple II in this area.

15
  • 2
    Because the Apple II uses 4116 chips, the requirement is quite small: 128 accesses will refresh the entire DRAM. (See my answer for details.) So no, none of the the "contortions" regarding mapping of video memory are related to refresh, beyond not having any video modes using a frame buffer of less than 128 bytes. (That's pretty trivial; 40x24 text mode needs a minimum of 960 bytes.) Nor does any the video design affect the DRAM address multiplexer, which is quite straightfoward anyway.
    – cjs
    Commented Mar 4, 2020 at 3:19
  • Also another point here: the screen refresh rate on the Apple II (once per 16.66 ms) is far too slow to refresh the DRAM (2 ms. max interval, per the 4116 data sheet). This answer is not correct, at least as far as the Apple II goes. It's unfortunate that it's still upvoted far past any of the more correct answers.
    – cjs
    Commented Mar 5, 2020 at 0:30
  • @cjs That just means the display refresh has to iterate over the DRAM rows multiple times per frame, at least 9 times. Woz was always keen to reduce component count, so the bizarre screen memory layout still plausibly resulted from a confluence of those two pressures.
    – Chromatix
    Commented Mar 5, 2020 at 2:33
  • No, it definitively did not. The DRAM refresh as designed is made no easier by the video circuitry; it would be exactly the same were the frame buffers linear, or even were the video circuitry completely replaced by just a 7-bit counter generating addresses used to read any part of RAM. See my answer for details. Raffzahn's answer provides a bit more detail than mine on the reasons for the funny frame buffer layout, also emphasising that it's nothing to do with DRAM refresh.
    – cjs
    Commented Mar 5, 2020 at 2:50
  • 1
    @SingleMalt DRAM arrays always need a row buffer, and it is built into the DRAM chip. Relying on DMA to perform DRAM refresh is a common technique, and generally just requires reading each row address in turn, which in early micros was a natural result of video scanout; the PC has a separate display module with its own memory, so the main memory has to be refreshed explicitly. More modern memory controllers have dedicated logic which activates a self-refresh function in FPM and later DRAM chips.
    – Chromatix
    Commented Jun 18, 2021 at 0:42
8

What exactly is DRAM refresh? Is it simply making sure a memory cell is accessed which gives it an electrical charge to keep it alive, or is it more like a 'read and re-write'?

Both.

DRAM stores it's information in the charge of a capacitor(*1). Capacitors leak. Chip capacitors leak faster than discrete ones,and small ones even faster (*2)- DRAM chips have to cope with both.

  • Reading may be destructive, like with core, and every read needs to be followed by an (internal) write, depending on the design.

  • Without reading, unlike core, it still needs a dummy read

Reading, and thus refresh, doesn't work on a cell (bit) base, but always accesses a whole row at once. Thus a single access will refresh all of them in a single cycle.

If this refresh mechanism is the reason for the non-linear memory layout of the Apple II video, then why? Is it because the gap of 64 lines was the amount of time that the even-phase would get for compute while the video circuitry was still displaying progressively?

No. The video memory layout is simply to allow savings within the video address generators used to walk thru memory to generate a frame. For a continuous refresh it's sufficient to address every row once per frame. This is guaranteed due screen refresh.

The whole addressing is the result of the counters used to perform multiple function.

First is simply addressing the bytes during a frame. During a frame the the video counters need to address 40 bytes per line and 262 lines per frame. Doing so the 'standard' way would require a 5 bit counter (0..39) and a 9 bit counter (0..261). Both not really common sizes. Common are 4 and 8 bit counters. So doing this would require at least five 4-bit wide - like a 74161.

Woz now interleaved them to get it down to only four (Position D11..D14) by using two of them as byte counters (D13/D14), but 'stealing the high bit of the second (D13) to form a 9 bit line counter with the other two (D11/D12).

Of course, same 4 chips could have been used to create a linear 13 bit address right way. But then a set of (expensive) comparators and more important another set of counters for timing line/frame timing would have been needed.

Woz' idea was to use them for both, addressing and timing. So the byte counter did not simply run until 40 for all bytes within a line, but 65 which is the line time, using the only first 40 to access. It is as well the value that lets the top bit of D11 flip, increasing the line counter by one. So this saves separate handling of end of line and increment to the next, as it simply carries over (*3).

So essentially it is about building a 16 bit counter and selecting the right bits to generate timing as well as an address. The 'odd' addressing could have been avoided by having timing and addressing handled by different counters, which meant that, for the line length, two additional 74161 would have been needed.

But there is more to it.

Instead of adding a separate refresh logic, needing it's own set of counters - and of course time to access, slowing video or CPU, Woz simply let the video do the refresh as well. This is in part done due the way the cells (rows) are assigned to addresses. A 4116 RAM chip uses a 14 Bit Address organized as 7 bit row and 7 bit column. By default one would assume to simply put CPU address A13..A7 as row (and A6..A0 as column). But Woz did use A12, A8, A7 and A3..A0 as row address (and the remaining as column). This seemingly wired scheme is in part due the fact that video doesn't cover 16 Ki (which would be needed when using A13..A7), but only 8 Ki (size of a highres screen). More so, a video scan over all 8 Ki would take more than the 2 ms 4116 timing allows as maximum timing between refresh (for each row). The way the addresses are assigned ensures that all 128 values are generated within 2048 cycles. At a clock frequency of ~1,024 MHz, this comes down to 2.038 ms, which is close enough to make it work reliable.

Of course while video (content) is only needed during the visible part of the picture, refresh should run all the time. As solution Woz let the address counters continue to address screen RAM during blanking and retrace. This time just discarding the values read.

For what its worth, how many chips did Woz actually save by doing this anyway?

Two 4-bit counters for line length (see above) (*4).

This article at I-Programmer notes:

He also cheated on the addressing for the memory mapped graphics to save two chips at the cost of a strangely mangled memory layout. For years to come users of the Apple II would wonder why memory adjacent memory locations didn't always control adjacent screen locations.

A quick browsing of I Woz didn't show up any relevant information.


*1 - With some some early models this is really a storage of an analogue value, thus DRAM could be used to hold more than one value per bit, like modern Flash. It has been exposed by a few nifty designs, but I guess RAM sizes grew too fast to let room for any serious exploit to generate serious level based applications like with Flash did.

*2 - Not really leak faster, but due their small capacity, the absolute load difference between a secure detection of a load and ambiguity is smaller, thus the time until it's reached is reached faster.

*3 - There is more to it regarding clock generation and timing, but that'll need a lot more space to describe.

*4 - Well, as usual the answer is not as easy when taking about savings, as they are never straight savings (which would mean they were surplus in the first place). In this case adding the two counters would have meant that the adder used for address generation (74283 at position E14) could be saved - but an additional mux would have been needed - so far this comes to a net saving of two IC, but then again this may have needed different glue logic, so the exact number saved is unknown unless we don't know the exact 'other' logic Woz would have used.

11
  • Refreshing once every 16.7ms frame would be too slow. Bits 0-4 cycle through all 32 possibilities every scan line, and 7-9 together advance through eight possibilities roughly once every eight scan lines, for a total repeat time of 64 scan lines (though I'm not sure what they do on the last six scan lines of a frame; that might push the time to 70 scan lines).
    – supercat
    Commented Mar 3, 2020 at 23:31
  • @supercat Refresh of every row for every DRAM device in the system happens not once per frame, but with every 128 bytes read from the video RAM. (Details in my answer.) So for high-res graphics you get a full DRAM refresh every four scan lines. It's actually text mode that's the bigger issue here, since reading 128 bytes there requires reading four rows of characters, which would be 32 scan lines. But even that is only about 65 microseconds, much less than the 2 ms max refresh interval of a 4116. The biggest gap of all is actually the vertical blank interval!
    – cjs
    Commented Mar 4, 2020 at 3:17
  • @cjs: What does the Apple do during vertical blank? I would think that since the total screen size is just over 256 scan lines, that 64 scan lines would fetch bytes in a pattern similar to the three displayed groups of 64 lines, but I'm not sure about the other six. Meeting a 2ms refresh interval would require that something be done for most of the vertical blanking interval, even if not necessarily for the "extra" six lines. By the way, a difficulty you didn't mention with trying to create a linear display is the fact that the bytes from each line of text have to be read out eight times.
    – supercat
    Commented Mar 4, 2020 at 17:01
  • 1
    @supercat cjs' assumption is true, the video address generator simply continues to access display data during retrace/blanking - with the value read being discarded.
    – Raffzahn
    Commented Mar 4, 2020 at 23:29
  • @supercat Reading each text row 8 times isn't particularly difficult as far as I can see; just drop the lowest three bits from your scan line counter when generating the memory address, though I suspect Woz may use something more clever. Regardless, I didn't mention it because it's irrelevant to this question: the video memory layout has nothing to do with DRAM refresh beyond ensuring the generator accesses all addresses xxxxx000 through xxxxx111 (x=don't care) at least once every 2 ms, which is trivial.
    – cjs
    Commented Mar 5, 2020 at 0:26

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .