Write-Through vs Write-Back Cache: What Are the Trade-Offs?

Write-through and write-back are the two primary cache write policies used in classical computer architectures to manage how modified data is propagated from a cache to lower levels of the memory hierarchy. Choosing between them involves a fundamental trade-off between memory bandwidth consumption, write latency, hardware complexity, and data consistency. Write-through prioritizes simplicity and immediate consistency at the cost of higher memory traffic, whereas write-back minimizes memory bandwidth usage and improves write throughput at the cost of added control logic and potential eviction delays.

How Write-Through and Write-Back Work

In a write-through cache, every write operation updates both the cache line (on a write hit) and the next lower level in the memory hierarchy (such as L2 cache or main memory) immediately. Because main memory always holds the most recent copy of the data, cache lines never become "dirty" relative to lower-level storage.

In a write-back (or copy-back) cache, a write operation updates only the cache line and sets a dirty bit associated with that line. The modified data is written to the lower memory level only when the dirty cache line is evicted to make room for another block, or when an explicit flush occurs.

Performance Trade-Offs

Write Latency and Buffering

On a write hit, a write-back cache completes the operation at cache speed, typically within a few clock cycles. A naive write-through cache would stall the processor until the slower lower-level memory acknowledges the write.

To mitigate this latency penalty, modern write-through implementations use a write buffer (a small FIFO queue between the cache and main memory). The processor writes to the cache and places the address and data into the write buffer, then continues executing. However, if the processor performs a burst of writes that fills the write buffer, it must stall until space becomes available.

Eviction Overhead and Read Misses

Write-through caches have a distinct advantage during cache misses: because all data in the cache is already synchronized with main memory, any clean line can be evicted immediately without writing it back.

In contrast, a write-back cache may encounter a dirty eviction on a cache miss. If the victim line has its dirty bit set, the cache must write that entire cache line back to lower memory before—or concurrently with—fetching the new line. This increases the miss penalty, though write-back buffers can hide much of this latency by deferring the writeback while the requested read proceeds.

Effective Access Time

The average memory access time (AMAT) for both policies can be modeled by accounting for hit time, miss rate, and miss penalty. For a write-back cache, the miss penalty includes the probability \(p_{\text{dirty}}\) that an evicted line is dirty:

\[\text{AMAT}_{\text{WB}} = t_{\text{hit}} + r_{\text{miss}} \cdot \left( t_{\text{miss}} + p_{\text{dirty}} \cdot t_{\text{writeback}} \right)\]

For a write-through cache, there is no dirty eviction penalty, but every write incurs a potential stall if the write buffer saturates:

\[\text{AMAT}_{\text{WT}} = t_{\text{hit}} + r_{\text{miss}} \cdot t_{\text{miss}} + p_{\text{write}} \cdot p_{\text{buffer\_full}} \cdot t_{\text{stall}}\]

where \(t_{\text{hit}}\) is the cache hit time, \(r_{\text{miss}}\) is the miss rate, \(t_{\text{miss}}\) is the base miss penalty, \(t_{\text{writeback}}\) is the time to write a dirty line back, \(p_{\text{write}}\) is the fraction of accesses that are writes, \(p_{\text{buffer\_full}}\) is the probability the write buffer is full, and \(t_{\text{stall}}\) is the stall duration.

Memory Bandwidth Trade-Offs

Traffic Generation

The most significant difference between the two policies lies in memory bus bandwidth consumption:

  • Write-through generates memory traffic on every write operation. If a program modifies the same variable in a loop 1,000 times, a write-through cache sends 1,000 write transactions to the lower memory level (unless a coalescing write buffer merges consecutive writes to the same address).
  • Write-back absorbs repeated writes to the same cache line within the cache itself. Those 1,000 modifications result in only a single cache-line writeback when the line is eventually evicted.

Granularity of Transfers

Write-through typically transfers only the modified word or bytes (e.g., 4 or 8 bytes) per write transaction. Write-back transfers an entire cache line (commonly 64 bytes) upon eviction, even if only a single byte in that line was modified.

Despite the larger transfer size per writeback, write-back almost always consumes less total bandwidth in workloads with high temporal and spatial locality, because multiple writes to different words within the same 64-byte line are coalesced into one writeback. Conversely, in workloads with poor locality—such as streaming writes that touch each cache line only once—write-back can approach or match the bandwidth usage of write-through.

Summary of Trade-Offs

Characteristic Write-Through Write-Back
Memory Bandwidth Usage High (every write hits lower memory) Low (coalesces repeated writes)
Write Hit Latency Higher (relies on write buffer) Very low (cache speed only)
Eviction Overhead None (lines are always clean) Higher (dirty lines must be written back)
Hardware Complexity Low (no dirty bits needed) Higher (requires dirty bits and writeback logic)
Data Consistency Strong (memory is always up to date) Weak (memory lags behind cache)

In practice, modern processors often combine both policies across different cache levels: L1 caches frequently use write-through (or write-back with a write-allocate policy) for simplicity and fast error recovery, while L2 and L3 caches almost universally use write-back to conserve precious off-chip memory bandwidth.