Search code examples
assemblyx86gnu-assembler

invalid instruction suffix for `mov' (movw %ax, %ebx)


When I try to compile the following program:

.globl _start
.section    .text

_start:     movw        $-23, %ax
            movl        $-1,  %ebx   # -1 = $0xffffffff
            movw        %ax,  %ebx

            movl        $1, %eax
            movl        $0, %ebx
            int         $0x80

I get this error message:

demo.s: Assembler messages:
demo.s:7: Error: invalid instruction suffix for `mov'

So, the root of the proglem lies here:

movw        %ax,  %ebx

But the thing is that I don't think what I'm doing is totally wrong plus that's the example used in the book I'm currently reading: Professional Assembly Language by Richard Blum (2005)


Solution

  • You didn't write, what you want to do with that program.

    First you put -23 into ax, then -1 into ebx, then you try to move ax into ebx, which is not valid on x86 processor, as ax is 16bit, and ebx is 32bit register. mov can't convert width of data during processing.

    To make it work there are two basic options.

    • if you want only lower 16b of ebx modified (by 16b from ax), you can do mov %ax, %bx, keeping upper 16b of ebx intact. (in your case the result will be -23 in ebx/bx/bl).

    • if you want to extend the 16b value into 32b value, you can do either:

      1. movswl %ax, %ebx # sign-extended conversion (movsx in Intel syntax)
      2. movzwl %ax, %ebx # zero-extended conversion (movzx in Intel syntax)

    In 1. the ebx (and bx and bl as well) will contain -23. In 2. the ebx will contain 0x0000FFE9, so ebx will be 65513, bx and bl will be -23 if treated as signed integer. Or 65513 for bx and 233 in bl when treated as unsigned integers.

    About the book... are you sure? Read that carefully again, must be a typo, or you are overlooking some tiny detail.