Hello and welcome back.
In this lesson we are going to learn x64 calling convention, also known as Microsoft Calling Convention.
So let's take a look at what it means.
Calling convention is a set of rules which determine how parameters are passed to functions, and how
they return.
Values are also handled.
Stack.
Example.
We have a function with four arguments: arg1, arg2, arg3, arg4.
According to Microsoft calling convention, you need to pass the first argument to -.
We're going to move the second argument to -, the third one to -, and the fourth one to -.
Then you have to allocate shadow space of 32 bytes.
Then you call the function.
So when the function runs, it will make use of all these arguments.
Now what if you have more than four arguments?
If you have more than four arguments, assuming we have eight arguments, then the remaining arguments
five, six, seven, and eight need to be pushed to the stack like this.
And then this will require a recalculation of the shadow space.
So normally in x64 environment we don't push arguments to the stack.
Instead, we move arguments directly into the stack using move statement.
So this will be the most common way to pass parameters using the stack.
So as usual, you notice here the first four is to move to the -.
- - - and -, but this time, instead of pushing to the stack, we will allocate space on the stack
for these four arguments which we are going to push to the stack.
So this argument six.
Argument five, sorry. Argument five will be moved to - plus 32. Argument six will be moved to - plus
40.
Argument seven will move to - 48, and argument eight will move to - plus 56.
Then only you call the function, but in this case you need to recalculate how much shadow space.
So the shadow space will be shadow space 32 plus four arguments times eight, because each of the arguments
takes up a quadword.
So we have four arguments will be 32, 32 plus 32 gives you 64.
So you need to allocate space in the stack for 64 arguments, for the shadow space and four for the
argument 5, 6, 7, 8.
If you only have five arguments, then you take one times eight.
That will give you 40.
That means sub - 40.
If you have six arguments, then it will be 32 plus 16.
Two times eight is 16.
So 32 plus 16 is 48.
That means it will be sub - 48.
And so on.
So this is how you calculate how much of the shadow space you need to allocate
when you have more than four parameters that you pass to the function.
So a diagram will make this easier to understand.
Now assuming that this is a stack here and this is a register.
So before the call is made, you will load your registers - with the first argument, - second argument,
- with the third argument, - with the fourth argument.
Thereafter, you will then allocate shadow space, and then you will also allocate four quad words
for the arguments.
So four times eight, 32 plus 32 here is 64.
So at the moment your - is pointing here.
The stack pointer - points to the bottom of the stack, and - points to the top of the stack.
Okay.
So now how do you pass arguments to the stack?
How do you now move the arguments to the stack?
You use the offset - plus 32 to access the fifth argument, - plus 40 to access the sixth argument,
- plus 48 for the seventh argument, and - 56 for eighth
argument.
Why 32?
Because the return, because the shadow space is of 32.
Since your - is at the top of the stack, so it must plus 32 to get to the fifth argument.
That is the reason why you plus 32 here to access the fifth argument.
So you will save a few arguments there directly instead of pushing.
Instead of pushing like this in reverse order, you move it directly inside.
Same thing with the sixth argument, sixth argument - plus 40, and so on.
So after the call is made, the return address will be pushed to the stack like this.
So return address is pushed to the stack.
And then after that, you will do a push - inside your new function.
And that will push the old address of the - into the stack itself, so that you can keep track
of where was the old stack frame.
So now the old - is here, so - will move to the top.
Then you will move - to -.
That will effectively move - right to the top
to point to the same location as the -.
So now - is pointing here, and this will always be remaining here throughout the execution of the
function.
But - is free to move around.
So we will use - as a base pointer to refer to any variables or arguments.
So in this case here, if you wanted to refer to the fifth argument inside the function, you will do
- plus 48.
Why?
Because from here to here is eight.
Here to here is 32.
So 40.
And then here to here another eight.
So 48.
If you want to access the sixth argument, then you would do
plus another eight, becomes - plus 56. If you want to access the seventh argument, is - plus 64, and
so on.
So then let's say after this you want to create local variables.
You can do so like this.
Let's say you want to create five local variables.
You will just move.
You do sub - 40.
Why 40?
Because five times eight is 40.
Each variable will be eight bytes or quadword.
So what you have here will be
1, 2, 3, 1, 2, 3, 4, 5.
So five times 8, 40.
That's how you do it.
And if you wanted to access these local variables, you would take the - minus eight to access the
first local variable.
Then to access the second local variable will be - minus 16, and so on.
So you notice that the - is very useful.
It is a base pointer for your stack, for your new stack frame.
So this is called a stack frame.
By the way, this is the old stack frame.
This is the new one.
So - will then be used to access all the arguments by taking the offset plus.
And to access the local variables, you take the offset minus like this.
All right.
So in the next lesson we will do some practicals so that all this will become clear to you.
That's all for this video.
Thank you for watching.