0

If I have to translate short int v[5] = {1,2,3,4,5} into assembly code how can I do it? It is ok if I'm doing something like this:

Enter 16,0
Mov ebp-4, 1
Mov ebp-8, 2
Mov ebp-12, 3
Mov ebp-16, 4

Thanks.

10
  • what assembler syntax is this? Intel syntax requires [] around memory references (from the operand order it looks like Intel syntax). And each assembler has subtle differences, MASM: mov word ptr [ebp-4], 1, NASM: mov word [ebp-4], 1 ... and you can put the values 2 bytes apart, as short int is int16_t (probably). Also if you read those values in memory, you will end with @ebp-16 address: 4, 3, 2, 1 ... The C source was 1, 2, 3, 4, 5 ... So you are very close, but it's not the same, you got principle right, now tune details. Try it in godbolt: godbolt.org/g/7woqUa Commented Jan 24, 2018 at 9:22
  • hey, thank you. I wanted for NASM ;) Commented Jan 24, 2018 at 9:24
  • what about " v dw 1,2,3,4,5 " ? Commented Jan 24, 2018 at 9:25
  • @Tommylee2k that's not usable for local variable stored in stack, only for global/static in .data. Andreea: adding "-fno-omit-frame-pointer" to the gcc options in the previous link will force it to use ebp notation, closer to your original source: godbolt.org/g/qv35Tp (if you are not experienced to spot how the esp can be exploited in the first variant, this one should be more readable to you -> but I strongly suggest to copy all the variants (including -O3 ones) into debugger, and single-step over them reasoning about their differences and how each works = will teach you a lot) Commented Jan 24, 2018 at 9:28
  • 1
    he didn't say he want's local variables ;-) tbh he didn't specify anything. we just reasoned this from his code snippet Commented Jan 24, 2018 at 9:30

1 Answer 1

2

You can do that, but as @Ped7g pointed out, you need qualifiers. v[0] is going to be 20 bytes lower in memory, so you'd have to write them in reverse order.

        enter   20, 0

; At this point ESP is the pointer to v[]

        mov     dword [bp-20], 1
        mov     dword [bp-16], 2
        mov     dword [bp-12], 3
        mov     dword [bp-8], 4
        mov     dword [bp-4], 5

The reason you have to use dword's is because imagine the contest of stack as follows;

2F 3D 17 0A 41 FF 16 18 03 22 19 0D 01 F3 D1 0C 12 02 EE 4A

using byte qualifier for byte [bp-4], 5 would only change 2F. DWORD however changes all 4 bytes and then becomes

05 00 00 00

To save program space, you could also

        push    bp
        mov     bp, sp
        push    5
        push    4
        push    3
        push    2
        push    1

There are caveats to this, but because the IA32 is structured, these will extend to 32 bits. Does use a lot less code though.

Declared outside a procedure, then it would become

    v:    dw    1, 2, 3, 4, 5
Sign up to request clarification or add additional context in comments.

1 Comment

You are defining v: dd 1, 2, 3, 4, 5 on the stack. It's possible to define shorts array in stack memory, even if the default push/pop operates with dwords, you can still even use push, like push 0x50004 push 0x30002 push 0x10000 to have word array at original esp-10 with 2B junk at esp-11 and esp-12 (or new esp+0, esp+1, and array is at esp+2 to esp+11). If you would check the godbolt links from my comments, the C compiler indeed will produce short array, in stack (but by using mov, not push).

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.