Calling conventions, Function call mechanism – Zilog ZUSBOPTS User Manual
Page 200

Calling Conventions
UM017105-0511
172
Zilog Developer Studio II – ZNEO™
User Manual
Calling Conventions
The C-Compiler imposes a strict set of rules regarding function calls. Except for special
run-time support functions, any function that calls or is called by a C function must follow
these rules. Failure to adhere to these rules can disrupt the C environment and cause a C
program to fail.
Function Call Mechanism
A function (caller function) performs the following sequence of tasks when it calls another
function (called function):
1. Save any of the registers R0–R7 that are in use and may be required after the call;
these registers may be overwritten in the called function.
2. Place the first seven scalar parameters (not structures or unions) of the called function
in registers R1–R7. Push parameters beyond the seventh parameter and nonscalar
parameters on the stack in reverse order (the rightmost declared argument is pushed
first, and the leftmost is pushed last). This places the leftmost argument on top of the
stack when the function is called. For a
varargs
function, all parameters are pushed
on the stack in reverse order.
3. Call the function. The call instruction pushes the return address on the top of the stack.
4. On return from the called function, caller pops the arguments off the stack or incre-
ment the stack pointer.
5. Restore any of the registers R0–R7 that were saved in step 1.
When a byte or structure of an odd size is pushed on the stack, only the byte or structure is
pushed. Future enhancements might introduce padding so that 16- or 32-bit objects are
located at an even offset from the frame pointer so avoid writing code that depends on the
alignment of data. If you are writing an assembly routine called out of C, it is recom-
mended that you declare parameters as
short
rather than
char
so that offsets to parame-
ters are not changed by such an enhancement.
The called function performs the following sequence of tasks:
1. Push the frame pointer onto the stack and allocate the local frame:
a.
Set the frame pointer to the current value of the stack pointer.
b. Decrement the stack pointer by the size of locals and temporaries, if required.
2. Save the contents of any of the registers R8–R13 (and possibly R14; see comment
below) that are going to be used inside this function.
3. Execute the code for the function.