5

Alright, so I am dealing with the following snippet of code:

push   %ebp
mov    %esp,%ebp   
push   %ebx
mov    0x8(%ebp),%eax 
movzwl %ax,%edx

So this behaves as expected when dealing with positive values. The value copied into %edx is the trailing 16 bits of %eax (or %ax).

However, if you put a negative number in, everything starts getting weird and it does not seem to be behaving as expected.

For example, if the value of %eax is -67043552, then the value copied into %edx is 65312.

I'm fairly new to assembly, sorry if this is an obvious misinterpretation on my part. Any help would be greatly appreciated.

Peter Cordes
  • 328,167
  • 45
  • 605
  • 847
ebensing
  • 6,409
  • 4
  • 18
  • 20
  • [`movswl`](http://www.felixcloutier.com/x86/MOVSX:MOVSXD.html) is available when you want to sign-extend a 2's complement signed value instead of zero-extending a binary unsigned value. (See also the [x86 tag wiki](http://stackoverflow.com/tags/x86/info). – Peter Cordes Jun 16 '16 at 08:11
  • Also, if you printed your numbers as hex, it would be a lot less confusing / more obvious what's going on. – Peter Cordes Jun 16 '16 at 08:12
  • Also, unless you actually need the full value in `%eax`, you should `movzwl 0x8(%ebp), %edx` directly instead of wasting an instruction doing it separately. Intel CPUs can handle `movzx` / `movsx` as just a load uop, with no ALU required. – Peter Cordes Jun 16 '16 at 08:18

1 Answers1

16

Remember that movzwl copies only the bits in %ax into %edx filling in the high 16 bits of %edx with zeros.

So %edx always ends up with a positive number less than or equal to 65535.

In detail: -67043552 in hex is fc00ff20. So if that is in %eax, then %ax contains ff20. If you move that into %edx with zero-extension, then %edx gets 0000ff20. That's 65312.

Ray Toal
  • 86,166
  • 18
  • 182
  • 232