Sign up to track your progress
Create an account to save your progress, complete exercises, and earn achievements.
Reading C++ Assembly
Learn to read the x86-64 assembly your C++ compiles into. Understand registers, the stack, calling conventions, control flow, how C++ features like virtual functions look at machine level, and what the optimizer really does to your code.
Support Free C++ Education
Help us keep this platform free for everyone! Your support enables us to create more high-quality lessons, exercises, and interactive content.
Course Curriculum
From C++ to Assembly (8 lessons)
What assembly is, why reading it is a superpower, how your code becomes machine instructions, how to read your very first listing, and how to generate assembly yourself.
What Is Assembly, and Why Read It?
Understand the difference between high-level code, assembly, and machine code, and why being able to read assembly makes you a better C++ programmer.
25 minutes
The Vocabulary of Assembly
A plain-language glossary of the core terms used throughout the course: instruction, mnemonic, operand, register, memory, immediate, label, and address.
15 minutes
The Compilation Pipeline
Follow your source code through preprocessing, compilation, assembly, and linking, and see exactly where assembly fits in.
25 minutes
Reading Your First Assembly Listing
Walk through the assembly of a tiny function line by line and learn the anatomy of an instruction.
35 minutes
The Common Instructions
Meet the dozen instructions that make up most assembly: mov and lea, the arithmetic ops, cmp and test, the jumps, and the function-call quartet push/pop/call/ret.
25 minutes
Two Dialects: Intel vs AT&T Syntax
The same instructions can be written two ways. Learn to recognise both and understand why this course uses Intel syntax.
20 minutes
Generating Assembly Yourself
Produce your own listings with g++ -S and objdump, explore Compiler Explorer, and use the in-editor assembly panel to inspect any code you write on this site.
25 minutes
Chapter 1 Summary and Quiz
Review the three levels of a program, the compilation pipeline, the anatomy of an instruction, the common instructions, and the two assembly dialects.
20 minutes
x86-64 Foundations: Registers and Instructions (7 lessons)
The general-purpose registers and their sub-register names, the core data-movement and arithmetic instructions, operands, addressing modes, and the lea instruction.
The General-Purpose Registers
Meet the 16 general-purpose registers, their conventional roles, and how to recognise them in a listing.
25 minutes
Register Sizes and Sub-Registers
How rax, eax, ax, and al name the same register at 64, 32, 16, and 8 bits, and why writing eax clears the upper half of rax.
25 minutes
Moving Data with mov
The mov instruction in its three forms: register to register, immediate to register, and loads and stores to memory.
25 minutes
Operands and Addressing Modes
Immediate, register, and memory operands, and the displacement[base + index*scale] addressing form.
30 minutes
lea: The Address Calculator
How lea computes an address without touching memory, and why compilers use it for fast arithmetic.
25 minutes
Chapter 2 Summary and Quiz
Review the register file, sub-register naming, mov, the arithmetic instructions, addressing modes, and lea.
20 minutes
References (1 resources)
Additional reference materials for this chapter
x86-64 Quick Reference
A cheat sheet of the general-purpose registers, the common instructions, the condition codes and their flags, and the System V argument registers. Keep it open while you read listings.
Control Flow in Assembly (6 lessons)
Comparisons and the flags register, conditional and unconditional jumps, and how if/else, loops, and switch statements compile.
cmp and the Flags Register
How cmp and test set the flags (ZF, SF, OF, CF) without storing a result.
25 minutes
Unconditional and Conditional Jumps
jmp versus je, jne, jl, jg and the rest, and which flags each one reads.
25 minutes
How if/else Compiles
Translating an if/else into a compare followed by a conditional jump over a block.
30 minutes
switch Statements and Jump Tables
How a dense switch becomes a jump table while a sparse one becomes a chain of compares.
30 minutes
Chapter 3 Summary and Quiz
Review the flags register, the conditional jump family, and the compiled shapes of if/else, loops, and switch statements.
20 minutes
Functions, the Stack, and Calling Conventions (8 lessons)
How the call stack works, the function prologue and epilogue, the System V calling convention, argument passing, return values, floating point in the xmm registers, and local variables.
What Is the Stack?
The call stack, the rsp register, push and pop, and how the stack grows downward in memory.
25 minutes
The Function Prologue and Epilogue
The push rbp / mov rbp, rsp setup and its matching teardown, and what a stack frame is.
25 minutes
The System V Calling Convention
Which registers carry arguments and return values, and the difference between caller-saved and callee-saved registers.
30 minutes
Passing Arguments in Registers
Watch several arguments land in rdi, rsi, rdx and friends just before a call.
25 minutes
Floating Point: The xmm Registers
Where float and double live: the xmm registers, the scalar SSE instructions like movss and addsd, and how floating-point arguments and return values are passed.
30 minutes
Local Variables on the Stack
How local variables are stored at fixed offsets from the frame pointer.
30 minutes
Chapter 4 Summary and Quiz
Review the stack, the prologue and epilogue, the System V calling convention, argument and return registers, the xmm registers, and local variable storage.
20 minutes
Data, Pointers, and Memory (6 lessons)
How pointers and references look in assembly, indexing into arrays, struct layout, global versus local storage, and a first look at the heap.
Pointers and References
A pointer is just an address in a register, and dereferencing it is a memory access.
25 minutes
Indexing into Arrays
How arr[i] becomes base + index*scale addressing, with the element size as the scale.
30 minutes
Struct Layout and Member Access
Member access as a fixed offset from a struct's base address, plus alignment and padding.
30 minutes
Global versus Local Storage
Globals in .data, .bss, and .rodata reached by RIP-relative addressing, versus locals on the stack.
25 minutes
A Glimpse of the Heap
What new and delete look like in assembly, and how they differ from stack allocation.
25 minutes
Chapter 5 Summary and Quiz
Review pointers and references in registers, array indexing, struct layout and padding, global storage sections, and heap allocation.
20 minutes
C++ Features in Assembly (6 lessons)
What distinctly C++ constructs look like at machine level: member functions and the hidden this pointer, constructors and destructors, virtual dispatch through vtables, templates, and a glimpse of exceptions.
Member Functions and the this Pointer
A member function is an ordinary function whose first, hidden argument is the object's address in rdi.
30 minutes
Constructors, Destructors, and RAII
Constructors and destructors are function calls you never wrote, and RAII is the compiler placing destructor calls on every exit path.
30 minutes
Virtual Functions and vtables
How a virtual call becomes a double indirection: load the vtable pointer, load the function pointer, call through it.
30 minutes
Templates in Assembly
Templates vanish at compile time: each instantiation is a separate, fully concrete function, often with a mangled name.
25 minutes
A Glimpse of Exceptions
What throw and try/catch add to a listing, landing pads and unwind tables, and why the happy path stays almost free.
25 minutes
Chapter 6 Summary and Quiz
Review the hidden this pointer, constructor and destructor calls, vtable dispatch, template instantiation, and the cost model of exceptions.
20 minutes
The Optimizer at Work (8 lessons)
Comparing -O0 to -O2 and the transformations behind the difference: constant folding, inlining, dead code elimination, loop unrolling, and vectorisation, capped by reading a full real-world function.
Comparing -O0 and -O2
The same function at both optimization levels, and what the optimizer strips away.
30 minutes
Constant Folding and Propagation
The compiler computing constant expressions at compile time so the program does not have to.
25 minutes
A Glimpse of Vectorisation
SIMD registers and packed instructions that process several elements at once.
30 minutes
Capstone: Reading a Real Function
A line-by-line walkthrough of a complete optimized function that combines a loop, array indexing, a function call, and a conditional, drawing on every chapter of the course.
40 minutes
Chapter 7 Summary and Quiz
Review the optimizer's core transformations and consolidate the reading skills from the whole course.
20 minutes