Что делает инструкция MOVZBL в синтаксисе IA-32 AT & T?
Что именно инструкция
movzbl 0x01(%eax,%ecx),%eax
делает?
Ответы
Ответ 1
Синтаксис AT & T разбивает movzx
командную мнемонику Intel в разных мнемониках для разных исходных величин (movzb
vs. movzw
). В синтаксисе Intel это:
movzx eax, byte ptr [eax+ecx+1]
то есть. загрузите байт из памяти в eax + ecx + 1 и установите нуль в полный регистр.
Кстати, у большинства инструментов GNU теперь есть опция switch или config, чтобы предпочесть синтаксис Intel. (Например, objdump -Mintel
или gcc -S -masm=intel
, хотя последний влияет на синтаксис, используемый при компиляции inline-asm). Я бы, конечно же, рекомендовал изучить его, если вы не собираетесь собирать AT & T для жизни. См. Также x86 теги wiki для большего количества документов и руководства.
Ответ 2
Пример:
mov $0x01234567, %eax
mov $1, %bl
movzbl %bl, %eax
# %eax == 0000 0001
mov $0x01234567, %eax
mov $-1, %bl
movzbl %bl, %eax
# %eax == 0000 00FF
Мнемоника:
- MOV
- Нулевое расширение
- Байт (8 бит)
- to Long (32-разрядный)
Существуют также версии для других размеров:
-
movzbw
: Байт (8 бит) в Word (16 бит)
-
movzwl
: Word (16-разрядный) до длинного (32-разрядный)
Как и большинство инструкций GAS, вы можете опустить символ последнего размера при работе с регистрами:
movzb %bl, %eax
но я не могу понять, почему мы не можем опустить предыдущую букву, например. выполняется следующее:
movz %bl, %eax
Почему бы просто не вывести его из размера операндов, когда они зарегистрированы, как для mov
и синтаксиса Intel?
И если вы используете регистры неправильного размера, он не может скомпилировать, например:
movzb %ax, %eax
Runnable Intel пример с утверждениями на GitHub.