How LLMs work

  • Beginner
  • 30 min
  • Lesson 1 of 3 in LLM foundations
  • Last verified

You will be able to

  • Trace what happens between a prompt and a streamed response: tokenize, embed, transformer blocks, logits, softmax, sample, append, repeat.
  • Explain why self-attention replaced RNNs: parallel training and direct links between tokens.
  • Describe how Query/Key/Value scoring, the causal mask and the sequence-length-squared score matrix work.
  • Explain prefill versus decode, why the KV-cache saves compute, and why it costs memory that grows with context length and concurrency.

At dusk, Harbour Terminus is nearly empty. Tobias clears his throat at the intercom and says, “The Lowtide Sleeper departs at 19:40 from Platform 2.” It is clear and correct, and a porter applauds quietly.

From the booth you can see what the concourse cannot: he says it one word at a time, and each word comes out only after the one before it.

Twenty minutes later he announces a call at “Pellam Cross”, in the same warm voice. There is no Pellam Cross on this line.

Between one word and the next, what is he working from?

Concept

An LLM is a next-token predictor. Feed it a sequence of tokens and it outputs a probability distribution over its vocabulary for “what comes next”. You pick one token (sampling, covered in Sampling parameters and the model landscape), append it to the sequence, and repeat. That loop, called autoregressive generationAutoregressive generationProducing text one token at a time, where each new token is appended to the input before the next step. This is why output length drives latency.Open the glossary entry, is the whole inference process. Chat formatting, system prompts and tool calls are just structure fed into the same loop.

The engine inside the loop is the transformerTransformerThe neural network design behind modern LLMs. Stacked blocks of self-attention and feedforward layers process all positions of the input in parallel during training and prefill.Open the glossary entry, built on self-attentionSelf-attentionA step where each token looks at the visible tokens, including itself, and takes a weighted mix of their information. It lets the model link distant words and runs in parallel across positions.Open the glossary entry. Every token computes a Query (“what am I looking for”), a Key (“what do I contain”) and a Value (“what do I offer”). A token’s Query is compared against the Keys of the tokens it is allowed to see, which produces attention weights. Those weights blend the Values. All tokens do this in parallel, in a few large matrix multiplications.

Why It Matters

RNNs and LSTMs read a sequence one token at a time through a hidden state. That has two costs. Training cannot be spread across a sequence on a GPU, because step 5 needs the result of step 4. And information from far back has to survive being squeezed through a fixed-size state again and again, so long-range links degrade.

Self-attention fixes both. During training every position is processed at once, and a token can read directly from any earlier token in one step, however far back it sits. This parallelism is a large part of why training at current scale became practical.

You will need this mechanism for almost every later cost and latency question in the course, so it is worth getting it right now.

Mental Model

Picture a room of experts (the earlier tokens), each wearing a sign that says what they know (Key). You hold a note describing what you need (Query). You compare your note against every sign, then take a weighted blend of what the relevant experts say (Value). Every token does this at the same time.

One rule changes the picture for text generation: you may only ask the experts who spoke before you. Nobody can read ahead to tokens that do not exist yet. That rule is the causal maskCausal maskA rule in attention that blocks each token from looking at later tokens. Without it the model could copy the answer it is supposed to predict.Open the glossary entry, and it is what makes next-token prediction possible.

Example

“The trophy didn’t fit in the suitcase because it was too big.” What does “it” refer to? Self-attention lets “it” connect directly to “trophy” regardless of distance. An RNN has to carry that link through every intermediate hidden state and often loses it.

Technical Deep Dive

  • Multi-head attention: several attention computations run in parallel (“heads”), each free to learn a different relationship (syntax, coreference, position). Their outputs are concatenated.
  • Positional encoding: attention has no built-in notion of order, so position information is injected explicitly (learned, sinusoidal or rotary schemes). Without it, “dog bites man” and “man bites dog” look the same to attention.
  • Causal masking: in a decoder-only LLM, a token may attend only to itself and the tokens before it. During training the mask lets the model learn next-token prediction at every position in parallel without peeking at the answer. During generation there is simply nothing later to look at.
  • Residual connections and layer norm: keep training stable across dozens of stacked transformer blocks.

Code

Python

def attention(Q, K, V, causal_mask):
    d_k = Q.shape[-1]
    scores = (Q @ K.transpose(-2, -1)) / (d_k ** 0.5)   # (n x n)
    scores = scores.masked_fill(~causal_mask, float("-inf"))  # no peeking ahead
    weights = softmax(scores, axis=-1)
    return weights @ V

scores is an n x n matrix, where n is the sequence length. Doubling the prompt quadruples the number of scores. Dividing by the square root of d_k keeps the dot products from growing with the vector size, which would push softmax into near one-hot outputs and starve the training signal. The mask sets “future” positions to minus infinity so softmax gives them zero weight.

A tiny attention heatmap

Text summary

This is a small, made-up example of how attention weights work, not output from a trained model. The sentence is “The cat sat and it purred”, and a person wrote the score table by hand so that the word “it” looks back at “cat”.

The heatmap is a table. Each row is one word asking which words to read, and each column is a word it could read. Every cell holds a weight between 0 and 1, and the weights in a row add up to 1 before rounding. They come from a softmax over the row’s scores.

Two controls change the table. The causal mask limits each word to itself and the words before it. When it is on, the cells above the diagonal are masked and get a weight of exactly 0, and each row’s weights are shared among fewer words. The temperature slider divides the scores before the softmax. The lesson divides by the square root of the key size, which is a fixed version of the same step; this slider is not the sampling temperature you set when you call a model. A low temperature makes the largest weight in a row bigger, and a high one spreads the weight more evenly.

Previous and Next pick which row the status line describes. Without JavaScript you see only this summary.

The interactive version needs JavaScript. The text summary above says what it shows.

Prefill and decode

Generation has two phases with different performance profiles.

  • PrefillPrefillThe first phase of a request, in which the whole prompt is processed in parallel. It sets time to first token and is usually limited by compute.Open the glossary entry: the model processes your whole prompt in one pass. All prompt tokens are known, so they are handled in parallel as large matrix multiplications, which keeps the GPU busy. Prefill sets the time to first token.
  • Decode: the model then generates one token per step. Each step has little new arithmetic to do, but it must read the model weights and the stored history from memory. Decode is typically limited by memory bandwidth, not compute (NVIDIA, 2023-11-17).

Mental model: prefill is reading the whole question once. Decode is writing the answer one word at a time while glancing back at your notes before each word.

Those notes are the KV-cacheKV cacheStored key and value vectors of earlier tokens, reused at each decode step so they are not recomputed. It saves compute but its memory grows with context length and concurrent requests. It is not a response cache.Open the glossary entry. Each past token’s Keys and Values never change once computed, so the server stores them and, at each new step, computes K and V only for the new token. Without the cache, every step would redo the projections for the entire history.

The cache is a trade: you save compute and pay in memory. Per token, it stores a Key and a Value for every layer:

KV-cache bytes = 2 x layers x KV-heads x head-dim x sequence length x batch x bytes per value

The NVIDIA article gives the same idea with hidden size in place of KV-heads times head-dim. Worked example, illustrative numbers, not a specific model: 32 layers, 8 KV-heads, head-dim 128, 16-bit values (2 bytes). That is 2 x 32 x 8 x 128 x 2 = 131,072 bytes (128 KiB) per token. An 8,192-token context is 1 GiB for one request. Ten concurrent requests at that length hold 10 GiB of cache before the model weights are counted.

Two consequences follow. Long contexts and many concurrent users compete for the same GPU memory, so the cache often caps how many requests a server can run at once. And techniques such as grouped-query attention (fewer KV-heads) exist mainly to shrink this cache. The KV-cache is not a response cache: it never returns a stored answer. It reuses stored Keys and Values so they are not recomputed, within one generation and, with prefix or prompt caching, across requests that share the same prompt prefix. We return to it, with serving costs, in Cost and latency optimization.

Diagrams

Diagram: The generation loop runs left to right: text is tokenized, embedded, passed through transformer blocks to produce logits, and one token is...

no

yes

Prompt text

Tokenize

Embeddings + position info

Stack of transformer blocks
(self-attention + feedforward)

Logits over vocabulary

Sample next token

Stop token or
max length?

Append token

Return generated text

Diagram summary: The generation loop runs left to right: text is tokenized, embedded, passed through transformer blocks to produce logits, and one token is sampled. If it is not a stop token it is appended and the loop restarts from the embedding step.
Diagram: The RNN passes information down a single chain, so t5 only sees t1 through the squeezed hidden state.

Decoder transformer: each token reads earlier tokens directly (causal)

t1

t2

t3

t4

t5

RNN: sequential chain, one step depends on the previous

t1

t2

t3

t4

t5

Diagram summary: The RNN passes information down a single chain, so t5 only sees t1 through the squeezed hidden state. In the decoder transformer each arrow points from a token to an earlier token it reads from directly, and no arrow points forward, which is the causal mask.
Diagram: One token’s embedding is projected into a Query, Key and Value.

Token embedding

Query

Key

Value

score = Q·Kⱼᵀ/√d for each visible earlier token j

Softmax → weights

Weighted sum of the visible Vⱼ

Updated token representation

Diagram summary: One token’s embedding is projected into a Query, Key and Value. Its Query is scored against the Keys of the tokens it may see, softmax turns the scores into weights, and the weights blend the Values into the token’s updated representation.
Diagram: At step 4 the cache holds the Keys and Values of tokens 1 to 3.

Generating token 5

Generating token 4

reused

K,V tok1

KV cache

K,V tok2

K,V tok3

Attend + emit token 4

KV cache

K,V tok4 ONLY (new)

Attend + emit token 5

Diagram summary: At step 4 the cache holds the Keys and Values of tokens 1 to 3. At step 5 those entries are reused and only token 4’s Key and Value are computed and added.

Real-World Application

Quadratic attention explains why “just use a huge context window” is not free. Doubling a prompt roughly quadruples the attention-score arithmetic during prefill. Total cost grows less steeply than that at short lengths, because the feedforward and projection layers scale only linearly with length. Memory is the second bill: the KV-cache grows linearly with context and with every concurrent request. When your API cost or latency jumps after users start sending longer prompts, look at both prefill time (time to first token) and cache memory (how many requests a server can hold).

Interview Perspective

Expect: “explain attention”, “why not RNNs”, “what happens during inference”, “what is a KV-cache and why does it matter”. A strong answer names the loop (logits, softmax, sample, append), says what Q, K and V do, and separates prefill from decode. The weak answer is “it just predicts words” with no mechanism, which reads as memorized trivia. A common follow-up is “how would you make attention cheaper for long context?” Sparse, sliding-window and linear attention are the usual families, and grouped-query attention and FlashAttention are the usual serving answers (later lessons touch cost optimization).

Provenance: Common industry pattern. These are standard topics for ML and GenAI roles, not a verified list for any named company.

Practice Questions

  • Basic: What does a transformer output at each generation step?
  • Intermediate: Why can’t attention alone tell “dog bites man” from “man bites dog”?
  • Advanced: Why does the KV-cache not help with the first token of a response, and what does it help with?
  • Product-Company: Your API cost tripled after users started sending longer prompts. Explain why in terms of attention cost and KV-cache memory, not just “more tokens = more cost”.

Activity

Trace by hand what happens to the sentence “The cat sat because it was tired”. Identify which earlier token “it” should attend to most strongly and why. Then write down which tokens the word “cat” is allowed to attend to under a causal mask, and what would go wrong in training if it could see “tired”.

Homework

Pick two real models you might use in production (for example a small open-weight model and a frontier API model). Find each model’s context window and, for the open model, its layer count, KV-head count and head dimension from its published config (stretch task; look for fields such as num_hidden_layers, num_key_value_heads and head_dim or hidden_size divided by num_attention_heads in the model’s config.json). Use the formula above to estimate KV-cache bytes per token and per full-length request. Write two sentences on what that means for how many users one GPU can serve. If a number is not published, say so instead of guessing.

Quick Revision

  • LLM = autoregressive next-token predictor; transformer = the architecture; self-attention = the mechanism.
  • Self-attention: Q/K/V per token, parallel, causal mask, n x n scores so cost is quadratic in sequence length.
  • Beats RNNs on parallel training and long-range links.
  • Prefill is parallel and sets time to first token; decode is one token per step and is usually memory-bandwidth-bound.
  • KV-cache saves recomputation and costs memory that grows with context and concurrency.

Check yourself

  • Walk-through: Without notes, describe the path from a prompt to the fifth generated token, and say what the KV-cache stores at that point.
  • Variation: The prompt becomes four times longer. What grows (prefill compute, KV-cache memory, time to first token), and what mitigations exist (grouped-query attention, FlashAttention, prompt caching)?
  • Common misconception: “It predicts the next word” with no distribution or decoding step; confusing the KV-cache with a response cache.

Practice

Test what you just read. Quizzes and cards are grouped by module: LLM foundations.

Check yourself11 questions on what this lesson set out to teach

Checking answers needs JavaScript. You can still read every question and option below.

0 of 11 answered

Keyboard: arrow keys move between options. Space or Enter selects the focused option.

ObjectiveTrace what happens between a prompt and a streamed response: tokenize, embed, transformer blocks, logits, softmax, sample, append, repeat.

  1. Question 1 of 11The transformer has just produced logits for the next position. What happens next in a normal generation loop?

    Choose one answer.

  2. Question 2 of 11A teammate says tool calls and system prompts need a different mechanism from ordinary text generation. What is the most accurate response?

    Choose one answer.

  3. Question 11 of 11A model's reply names a station that is not on the route, in the same fluent tone as the correct names around it. Which description of the generation loop best fits what happened?

    Choose one answer.

ObjectiveExplain why self-attention replaced RNNs: parallel training and direct links between tokens.

  1. Question 3 of 11What is the main reason self-attention replaced RNNs for large language models?

    Choose one answer.

  2. Question 10 of 11A colleague proposes replacing a transformer with an RNN to save compute on a long-document training job. Which point best explains why this would likely hurt?

    Choose one answer.

ObjectiveDescribe how Query/Key/Value scoring, the causal mask and the sequence-length-squared score matrix work.

  1. Question 4 of 11Which statement about information flow is correct for a decoder-only LLM generating text?

    Choose one answer.

  2. Question 5 of 11You double the prompt length. What happens to the number of attention scores computed in a layer during prefill?

    Choose one answer.

  3. Question 6 of 11In scaled dot-product attention, what is the Query compared against, and what is blended using the resulting weights?

    Choose one answer.

ObjectiveExplain prefill versus decode, why the KV-cache saves compute, and why it costs memory that grows with context length and concurrency.

  1. Question 7 of 11Which statements about the KV-cache are true? Select all that apply.

    Choose all that apply.

  2. Question 8 of 11A model uses 128 KiB of KV-cache per token. You serve 4 concurrent requests, each with 2,048 tokens of context. About how much cache memory is that, excluding model weights?

    Choose one answer.

  3. Question 9 of 11Users sending very long prompts see a long wait before the first word appears, but once text starts streaming it flows smoothly. Which phase is most likely responsible for the wait?

    Choose one answer.