The one thing to understand first
MVCC needs to answer one question billions of times a day: did the transaction that wrote this row commit or abort? A row’s xmin/xmax only tell you which transaction touched it — not its fate. The fate lives in a tiny separate ledger called the commit log (clog), stored on disk in pg_xact/ and cached in memory through a small machine called an SLRU. Understanding this pair explains hint bits, the subtransaction “cliff”, and several mysterious sources of CPU and I/O.
Two bits per transaction
The commit log lives in src/backend/access/transam/clog.c. For every transaction id it stores just two bits of status:
00 — in progress (or never recorded)
01 — committed
10 — aborted
11 — sub-committed (a subtransaction whose outcome depends on its parent)
Two bits means CLOG_XACTS_PER_BYTE = 4 transactions pack into a single byte. TransactionIdSetTreeStatus() writes a transaction’s fate at commit/abort; TransactionIdGetStatus() reads it back during visibility checks. That is the whole interface: set a fate, get a fate.