Common
1. Function calls
General overview of steps
Push function (to call) arguments to the stack
Load function address in the
EIP
Save current
EIPbefore updating it to point to new function address
Move
EBPto the top of new stack frame
Save current
EBPbefore updating it to point to current value inESP
Allocate space for the new stack frame
Move
ESPdown (to lower address)
Execute function
Erase the stack frame used by the function
Increment
ESPto point to the top of the stack frame (EBP)
Restore
EBPRestore
EIP
Return from function
Remove arguments from stack
Increment
ESP
Following the steps outlined in the textbook above regarding function calls, I will list out the corresponding x86 (32-bit) assembly codes.
Important!!
Note that for this example, we will draw the memory layout with the highest address at the top, while the lower addresses appear at the bottom visually. However, the
EBPandESPwill still point to the higher and lower addresses of the stack frame respectively.This means that the
EBPwill point to the "top" of the stack frame, while theESPwill point to the "bottom"
1.1 Push arguments on the stack
Remember that x86 passes arguments by pushing them onto the stack

push arg1 ; push first arg1 to stack
push arg2 ; push second arg2 to stack
As we can see from the stack content after the instruction,
arg2is pushed first beforearg1. This is because arguments are pushed onto the stack in reverse order
1.2 Call the function
This step can be broken down into 2 separate assembly commands:
pushandjmp
1.2.1 Push the old EIP on the stack
Since the value in the
EIPregister will be changed to point to the function address, we need to save its current value onto the stack before we overwrite it with a new value
push eip
1.2.2 jmp to the function address
jmp <func_addr>State of the memory AFTER instruction
The above jmp instruction simply points the EIP to the address given as argument. In this case, it will be the address of the "test" function.

1.3 Save current EBP value, before updating to point to new stack frame
EBP value, before updating to point to new stack frameThis step can be broken down into 2 steps, first we push the
EBPto the stack, before copying the value of the currentESPto theEBP
1.3.1 Push current EBP to stack
push ebp
1.3.2 Copy value of ESP to EBP
mov ebp, espNow, the EBP will point to the same address referenced by the ESP :

This will allow the EBP to point to the bottom (or top if seen visually from this diagram — remember the drawing convention in this example) of the (higher address) of the new stack frame of the "test" function.
1.4 Allocate new space for the new stack
This is performed by growing the stack (moving the
ESPto the lower address). The compiler will decide how far theESPshould be decremented, based on the complexity of the function to be called. In this example, we will assume theESPis decremented by 8 bytes:
sub esp, 0x8
1.5 Execute the function
Now, any local variables and any other necessary data can be saved in the new stack frame
The
EBP(pointing to the top of the stack frame) can be used as a point of reference to find other variables on the stack

1.6 Erase the stack frame used by the function
After the function is complete, the variables will be erased/removed by incrementing the
ESPto point to the value stored in theEBP
mov esp, ebp
Note that the local variables are actually still present physically on the stack. However, it is treated as "removed" due to the position of the ESP 
1.7 Restore value of the old EBP
EBPpop ebpThis instruction restores the value of the
EBPto point to the stack frame before the function call ("main")The
ESPwill also be incremented to remove the storedEBPvalue from the stack

1.8 Return from function
This step can be broken down into 2 separate assembly commands: pop and jmp 
1.8.1 Pop stored value of EIP
pop eipThis restores the value of the
EIPof the calling function

1.8.2 jmp back to the calling function
jmp <func_addr>1.9 Remove arguments from the stack
add esp, 0x8
Last updated