Question

I've created this simple and pointless assembly (Y86) code to see if I understand everything that's happening in the stack when the instructions call, pushl, popl and ret are used.

Like I said, this code is pointless, it's just for testing/learning purposes. Although, all memory addresses were correctly (hopeful) calculated and are not random.

The assembly code is the following:

     | .pos 0
0x00 |   irmovl Stack, %esp
0x06 |   rrmovl %esp, %ebp
0x08 |   irmovl $5, %eax
0x0E |   call func
0x13 |   halt
0x14 | func:
0x14 |   pushl %ebp
0x16 |   rrmovl %esp, %ebp
0x18 |   pushl %eax
0x1A |   popl %eax
0x1C |   popl %ebp
0x1E |   ret
     | .pos 50
0x32 | Stack: .long 0

The following is my best to draw a stack and explain what each step (instruction) does with the stack. Please note that I used SP and BP to refer to %esp and %ebp respectively cause they are used a lot and makes it easier to read.

What I want to know is if I got everything above right or if I missed anything. Please feel free to copy/paste whatever you want and fix some step(s) in your answer.

Also note that my understanding of this is very important, I have an exam Monday for which I need to be prepared and I would like the best answer you can give me. Depending on your answers, I might (or not) have some related questions that we shall take care in the comments section.

- INSTRUCTION: irmovl Stack, %esp
- INSTRUCTION: rrmovl %esp, %ebp
  1) Point %esp (SP) and %ebp (BP) to Stack

     |  ...  |
0x2E |-------|
     |       |
0x32 |-------| <--- SP & BP

- INSTRUCTION: irmovl $5, %eax
  1) Sets %eax = 5

- INSTRUCTION: call func
  1) Decrements SP by 4 (0x32 -> 0x2E)
  2) Saves return address (0x13) in memory location pointed by SP (0x2E)
  3) Jumps to "func" memory address (0x14)

     |  ...  |
0x2A |-------|
     | 0x13  |
0x2E |-------| <--- SP
     |       |
0x32 |-------| <--- BP

- INSTRUCTION: pushl %ebp
  1) Decrements SP by 4 (0x2E -> 0x2A)
  2) Saves BP value (0x32) in memory location pointed by SP (0x2A)

     |  ...  |
0x26 |-------|
     | 0x32  |
0x2A |-------| <--- SP
     | 0x13  |
0x2E |-------|
     |       |
0x32 |-------| <--- BP

- INSTRUCTION: rrmovl %esp, %ebp
  1) Sets BP = SP (0x32 -> 0x2A)

     |  ...  |
0x26 |-------|
     | 0x32  |
0x2A |-------| <--- SP & BP
     | 0x13  |
0x2E |-------|
     |       |
0x32 |-------|

- INSTRUCTION: pushl %eax
  1) Decrements SP by 4 (0x2A -> 0x26)
  2) Saves %eax value (5) in memory location pointed by SP (0x26)

     |  ...  |
0x22 |-------|
     |   5   |
0x26 |-------| <--- SP
     | 0x32  |
0x2A |-------| <--- BP
     | 0x13  |
0x2E |-------|
     |       |
0x32 |-------|

- INSTRUCTION: popl %eax
  1) Saves value (5) in memory location pointed by SP (0x26) in %eax
  2) Increments SP by 4 (0x26 -> 0x2A)

     |  ...  |
0x22 |-------|
     |   5   |
0x26 |-------|
     | 0x32  |
0x2A |-------| <--- SP & BP
     | 0x13  |
0x2E |-------|
     |       |
0x32 |-------|

- INSTRUCTION: popl %ebp
  1) Saves value (0x32) in memory location pointed by SP (0x2A) in %ebp
  2) Increments SP by 4 (0x2A -> 0x2E)

     |  ...  |
0x22 |-------|
     |   5   |
0x26 |-------|
     | 0x32  |
0x2A |-------|
     | 0x13  |
0x2E |-------| <--- SP
     |       |
0x32 |-------| <--- BP

- INSTRUCTION: ret
  1) Jumps to memory address (0x13) in memory location pointed by SP (0x2E)
  2) Increments SP by 4 (0x2E -> 0x32)
Was it helpful?

Solution

As far as I can tell you've got it all right.

One minor point I can make is that it is probably more intuitive to write the addresses above the value at those addresses. That is:

0x2E |-------|
     | 0x13  |
0x32 |-------|

The reason being that the address range covering the value (0x2E,0x2F,0x30,0x31) goes towards the next address 0x32.

Of course, you might want to use the notation expected by your teacher when doing the exam.

OTHER TIPS

You got it right.

What you are doing is exercising a function call using standard caller-callee conventions, creating a frame for the callee. You then perform a simple push and pop of a register before returning to the caller. This is totally correct and your understanding is correct (see http://y86tutoring.wordpress.com/2012/10/31/functioning-stacks/ for details)

Everything looks good. Only suggestion is that you do not need to define an 0x0000 word on the stack. Simply defining the Stack label would have done it.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top