Write-Allocate vs No-Write-Allocate: Write-Miss Behavior, Traffic and Pairing Compared

Write-allocate and no-write-allocate are policies that decide whether a line is brought into the cache when a write misses. With write-allocate, the cache first reads the line from the level below and then performs the write in the cache. With no-write-allocate, the line is not fetched and the write is sent straight to the level below. This is a separate choice from write-back vs write-through, which decide when a write that hits reaches the level below, but write-allocate is usually paired with write-back and no-write-allocate with write-through.

AspectWrite-allocateNo-write-allocate
On a write missReads the whole line from the level below, places it in the cache, then writes into itLeaves the cache untouched and sends the write directly to the level below
Line fill (read)Required. On multicore systems it is a read for ownership (RFO) that invalidates other cores' copies before the write, so a store miss looks like a read on the memory busNot needed; only the written data is sent to the level below
Usual pairingWrite-back: later writes to the fetched line hit and are absorbed without memory traffic, which pays back the cost of the initial readWrite-through: every write goes to the level below anyway, so fetching the line would not reduce write traffic
Traffic to the level belowLower when the same line is written many times or the written data is read backEach missing write goes out every time, but no extra reads are generated
Large write-only data (clearing memory, writing output)Each line is read only to be overwritten and later written back, roughly doubling traffic, and useful data is evicted from the cacheNo reads and no cache pollution, so it suits this kind of data
Reading right after writingThe line is in the cache, so the read hitsThe line is not in the cache, so the read misses and fetches it
Implementation techniquesFor write-only data, non-temporal (streaming) stores bypass the cache and send combined writes straight to main memory; some ISAs also have an instruction that zeroes a whole line without reading its old contentsA write buffer hides write latency, and it often merges several writes to the same line into one transfer
Where it is usedCommon in write-back caches; most CPU L1 to L3 caches are write-backCommon in write-through caches, such as a small L1 backed by a write-back L2, or simple embedded processors

Figures are typical orders of magnitude and vary by process generation and product.

When to use which

Write-allocate
When written data will soon be read or written again, such as a loop updating array elements: writes with temporal locality.
No-write-allocate
When writing a large amount of data that will not be read back for a while. It avoids useless reads and keeps the cache free for useful data.
In software
Even with a write-allocate cache, non-temporal stores avoid the line reads for large write-only buffers. The written data does not stay in the cache, though, so reading it back immediately is slower.

FAQ

What is the difference between write-allocate and no-write-allocate?

On a write miss, write-allocate loads the line into the cache and then writes it in the cache. No-write-allocate does not load the line and writes directly to the level below.

Does write-through always use no-write-allocate?

Not always. How a write hit is propagated (write-back or write-through) and whether a line is fetched on a miss are separate choices. In practice, though, write-through is usually paired with no-write-allocate and write-back with write-allocate. In a write-through cache, a store that hits updates the cached copy and is also written to the level below; a store that misses is normally sent straight down without fetching the line.

Why is write-allocate slow for write-only data?

Because each line that will only be overwritten is first read from main memory. The read plus the later write-back roughly doubles the traffic and also evicts other data that would be reused. Non-temporal stores avoid this read.

Check your understanding

Which policy, on a write miss, writes directly to the lower level without loading the line into the cache?

  1. AWrite-allocate
  2. BWrite-back
  3. CNo-write-allocate
Show answer and explanation

Answer: C. No-write-allocate

Writing straight to the lower level on a write miss without loading the line is no-write-allocate, commonly paired with write-through. It avoids useless fetches for data that is written once and not read back. Write-allocate instead loads the line and then writes it, which pays off when written data is soon reused, so it is commonly paired with write-back. Write-back governs when hits are propagated to memory, a separate axis from whether a miss loads the line.

When writing out a large amount of data that will not be read back for a while, what is the main benefit of non-temporal stores that bypass the cache?

  1. AThe written data stays in the cache longer and is faster to read later
  2. BThe cache is not filled with data that won't be reused
  3. CWrite ordering is no longer guaranteed, making program bugs easier to find
Show answer and explanation

Answer: B. The cache is not filled with data that won't be reused

Ordinary stores with write-allocate fetch the line from memory before writing, so even write-only data costs read traffic and evicts other data that will be reused. Non-temporal stores combine writes and send them straight to memory, leaving the cache unpolluted and skipping useless fetches. The data does not stay in the cache, so reading it back soon would be slower. Changed ordering semantics are a caveat, not a benefit.

For code that writes to the same line many times, why is a write-back cache more advantageous than write-through?

  1. AWrites complete within the cache, and memory is written only once when the line is evicted
  2. BMemory is updated on every write, so no work is needed at eviction
  3. CCache and memory always match, so no coherence management is needed
Show answer and explanation

Answer: A. Writes complete within the cache, and memory is written only once when the line is evicted

A write-back cache absorbs repeated writes to the same line within the cache and writes the dirty line back just once on eviction, greatly reducing memory traffic and power. Updating memory on every write is the write-through behavior, which generates traffic each time the line is written. Cache and memory always matching is also write-through; with write-back they differ for a while.

  1. Which correctly describes the write-back policy for caches?
  2. What is the main purpose of a write buffer in a write-through cache?
  3. In a write-back cache, what is the role of the dirty bit attached to each line?

Practice Memory Hierarchy questions

Key terms explained

Write-allocate
A policy that, on a write miss, first brings the line into the cache and then writes it. Usually paired with write-back; writing directly to the lower level without fetching is called no-write-allocate.
Write-through
A write policy that writes to the level below (such as main memory) at the same time as the cache. The lower level stays up to date, but write traffic is heavy, so it is paired with a write buffer.
Cache line
The unit in which data moves between a cache and the level below, also called a cache block. Many CPUs use 64 bytes, and the low address bits give the position (offset) within the line.
Cache memory
Fast, small memory placed close to the CPU. It holds frequently used data to bridge the speed gap with main memory. Mostly built from SRAM.
Temporal locality
The tendency to access the same data or instructions again soon after a first access, as with variables reused inside a loop. One of the reasons caches work.
Cache coherency
In a multicore CPU, the mechanism that keeps copies of the same address in different cores' caches consistent, for example by invalidating other copies when one core writes.

Related comparisons