The real steps inside the algorithm — explained with analogies, not math papers.
Step 1
SHA-256 can only work on data in 512-bit chunks — think of those as fixed-size boxes. But your message is almost never exactly the right size. So the first step is padding: you add extra filler to the end of your message until it fits perfectly into a whole number of boxes. It's like packing a moving truck — you stuff padding around your furniture so everything fills the space exactly.
Follow the data
Your message
Any length — could be 3 bytes or 3 gigabytes
Padded message
A "1" bit, then zeros, then the original length — now a multiple of 512 bits
Parsed into blocks
Block 1 (512 bits) → Block 2 → Block 3 → ...
Why the original length?
The last 64 bits of the padding always store how long your original message was. This prevents an attacker from adding extra data to a padded message and getting the same hash — the length would be wrong.
Step 2
Each 512-bit block gets split into 16 words (32 bits each). But the compression function needs 64 words to do its job. So SHA-256 takes those 16 original words and generates 48 more by mixing, shifting, and combining the ones it already has. It's like dealing 16 cards face-up, then creating 48 more by combining the values on the existing cards.
The 512-bit block is carved into 16 pieces of 32 bits each — called W0 through W15. These are the raw ingredients from your message.
For each new word W16 through W63, SHA-256 picks two earlier words, runs them through small mixing functions (called σ0 and σ1), and adds them together. Each new word depends on words that came before it.
These 64 words become the fuel for 64 rounds of mixing. One word per round — like adding one ingredient at a time to a recipe.
Fun fact
This expansion is what makes SHA-256 so thorough — by the time it's done, every single bit of your original message has influenced every part of the hash. Change one bit, and the whole schedule changes, which cascades through all 64 rounds.
Step 3
Imagine 8 cups labeled a through h, each holding a number. In every round, the cups get shuffled: some values are mixed together with bitwise math, a word from the schedule is stirred in, and a special constant is added. Then the whole row shifts over. After 64 rounds of this, the original values are unrecognizable.
The 8 working variables
Eight 32-bit values that get scrambled through 64 rounds. Each round mixes in one scheduled word and one constant.
64 rounds of mixing
64 rounds — each one stirs in a word from the schedule and a constant from the primes
T1 combines the current values of e, f, g, h, plus the round constant and the scheduled word. T2 mixes a, b, and c. These use bitwise operations — rotations, shifts, XOR, AND — that are cheap for hardware but deeply scramble the data.
Every variable moves down one position: g gets the old f, f gets the old e, and so on. The old h is discarded (its contribution is already baked into T1).
a gets T1 + T2, and e gets the old d + T1. These two injection points ensure every round changes multiple variables at once.
After 64 rounds, the 8 variables are thoroughly mixed. Each output bit depends on every input bit — this is the "avalanche effect" that makes hashing work.
Where do the constants come from?
The 8 initial values come from the square roots of the first 8 prime numbers (2, 3, 5, 7, 11, 13, 17, 19). The 64 round constants come from the cube roots of the first 64 primes. Using irrational numbers means there's no hidden pattern an attacker could exploit — it's a "nothing up my sleeve" design.
Step 4
After the compression function finishes one block, its output becomes the starting state for the next block. It's like a relay race: the first runner hands a baton to the second, who hands it to the third. Each runner (block) changes the baton (state). The final runner's baton is the hash.
Each block feeds into the next
IV (initial values) → compress block 1 → compress block 2 → ... → final hash. Strictly sequential — no shortcuts.
Here's the design quirk: the final hash output is the internal state. That means if you know the hash of a message, you know the exact state the algorithm ended in — and you can keep going, compressing more blocks as if they were part of the original message. This is called a length extension attack. Modern hash functions like BLAKE3 fix this by processing the final block differently.
Fun fact
The Merkle-Damgård construction is named after Ralph Merkle and Ivan Damgård, who independently proved it secure in 1979 and 1989. It's a brilliant design that has one job: make it possible to hash data of any length using a fixed-size compression function. SHA-256, SHA-1, and MD5 all use it.
Step 5
After the last block is compressed, the 8 working variables hold the final state. SHA-256 simply concatenates them — lines them up end to end. Eight 32-bit numbers → one 256-bit hash → written as 64 hexadecimal characters. That's your fingerprint.
8 × 32 bits = 256 bits
8 working variables
a • b • c • d • e • f • g • h
Concatenate
Line them up: a || b || c || d || e || f || g || h
256-bit hash
e3b0c44298fc1c14...d57816d21d5b202d
The avalanche effect
Change a single bit in the input and, on average, half the bits in the output will flip. After 64 rounds of mixing per block, plus the message schedule expansion, every output bit depends on every input bit. That's what makes SHA-256 a good hash function — even though the algorithm is completely deterministic, the output looks random.
The takeaway
SHA-256 is an elegantly simple machine: pad your data, expand each block into 64 words, crush it through 64 rounds of mixing, chain the result into the next block, and concatenate the final state. The design is proven and reliable — but it's a chain. Every block must wait for the one before it. On modern hardware with many cores, that's the bottleneck that BLAKE3 was built to solve.