Ok, this all depends on the ABI you are using. If it is anything similar to SystemV x86 Abi (the one in 32-bit linuxes). It should look like what you have described. (I have modified my answer to match what the wikipedia describes for LC-3)
first of all, you reach main()
, and have 4 local variables, each of one is an int
. (Assuming each int
is 4 bytes, and stack aligned to 4 bytes), they will be stored in:
0xEFFC: a
0xEFF8: b
0xEFF4: c
0xEFF0: x
Then you call a function, namely func()
. The LC-3 abi says that the parameters must be passed on the stack, from rigth to left:
0xEFEC: z --> c
0xEFE8: y --> b
0xEFE4: x --> a
Then you should save space for the return value, put the return address, and save your R5:
0xEFE0: Return value
0xEFDC: Return address to main
0xEFD8: Space for R5
Local variables again:
0xEFD4: p
0xEFD0: q
0xEFCC: r
On modern systems, the return value can be passed in registers (like EAX). It depends on your ABI where to pass it. Probably it can be returned on the stack too.
Another thing is that each function can create an stack frame, pushing into the stack the parent's Base Stack Address, and assuming their stack starts from that address.
You should probably have a document in where all these things are defined.