What does sub $0x28, %rsp at the beginning of a function mean and how do you figure out what the stack space is used for?
It carves out local-variable space on the stack; the hex amount is the byte count (0x28 = 40 bytes), so subtracting from %rsp grows the frame downward.
* sub $0x28, %rsp carves 40 bytes below the return address; the frame grows downward and the new %rsp is the bottom. *
sub $N, %rsp is how a function reserves room for its locals (the stack grows toward lower addresses, so subtracting allocates). To figure out what those bytes hold, watch how the function later reads and writes them. If you see accesses at (%rsp), 4(%rsp), 8(%rsp), those are individual local variables; if the function passes %rsp (or a lea of it) to something like read_six_numbers, the space is a buffer — here a 6-int array needing 24 bytes, with the extra bytes serving as alignment padding so the whole frame stays a multiple of 16.
Common stack sizes and what they suggest:
| Allocation | Likely use |
|---|---|
sub $0x8 |
Alignment padding only |
sub $0x10 |
1-2 local variables or alignment |
sub $0x18 - $0x28 |
Small array or multiple locals |
sub $0x100+ |
Large buffer (string, array) |
Reading locals in GDB:
(gdb) x/6d $rsp
(gdb) x/10xg $rsp
Tip: The total stack frame size = sub amount + (8 bytes per push). This must be a multiple of 16 for alignment.
Go deeper: