This is an old revision of the document!
In another scenario, we will create a library with functions performing the simple calculations on integers and floating-point numbers. We will write functions for adding six integers and six floating-point values. This example will present argument passing through the registers and also through the stack, showing the order and addresses of stack-allocated arguments. The simplest version of a function adds six integers without advanced stack manipulation. Let's present the code of a function first. It takes the first four arguments from registers, and the latter two from the stack. Please note that for each argument, there is an 8-byte space reserved on the stack.
.code ; --------------------------------- ; sum of six integer arguments ; this is a leaf function ; does not need to reserve shadow space ; arguments as passed by MSVC ; a = RCX ; b = RDX ; c = R8 ; d = R9 ; e = [RSP + 28h] ; f = [RSP + 30h] ; --------------------------------- sum_6_int proc mov rax, rcx add rax, rdx ; a + b mov rcx, r8 add rax, rcx ; + c mov rcx, r9 add rax, rcx ; + d mov rcx, QWORD PTR [rsp + 28h] add rax, rcx ; + e mov rcx, QWORD PTR [rsp + 30h] add rax, rcx ; + f ret sum_6_int endp
The stack from a function perspective looks like in a fig.
The caller passes arguments according to the Windows x64 ABI. The responsibility of the caller is also to reserve the shadow space for all arguments before the call.