Почему можно было бы использовать “movl 1$, %eax” в противоположность, скажем, “movb 1$, %eax”

Как заголовок указывает, почему можно было бы использовать "movl 1$, %eax" в противоположность, скажем, "movb 1$, %eax", мне сказали, что movl обнулит высокого уровня биты %eax, но не является %eax регистр, это эквивалентно размеру wordsize системы? подразумевать, что movl находится в действительности целочисленная операция (и не длинное?)

Я ясно немного смущен всем этим; Спасибо.

20
задан starblue 15 December 2009 в 13:30
поделиться

6 ответов

в отличие, скажем, от "movb $ 1,% eax"

Эта инструкция является недействительным. Вы не можете использовать eax с инструкцией movb. Вместо этого вы должны использовать 8-битный регистр. Например:

movb $ 1, $ al

но не% eax регистр, который эквивалентный размеру системы словесный размер?

Нет. EAX всегда будет 32-битным значением, независимо от размера системного регистра.

Вы путаете размеры переменных C с размерами регистров. Размеры переменных C могут меняться в зависимости от вашей системы и компилятора.

Сборка проще, чем C. В сборке GAS инструкции имеют суффиксы с буквами «b», «s», «w», «l», «q» или «t», чтобы определить, какой размер операнда обрабатывается. .

* b = byte (8 bit)
* s = short (16 bit integer) or single (32-bit floating point)
* w = word (16 bit)
* l = long (32 bit integer or 64-bit floating point)
* q = quad (64 bit)
* t = ten bytes (80-bit floating point)

Эти размеры постоянны. Они никогда не изменятся. al всегда 8-битный, а eax всегда 32-битный.

41
ответ дан 29 November 2019 в 22:50
поделиться

На 32-битной машине% eax - это 4-байтовый (32-битный) регистр. movl запишет все 4 байта. В вашем примере он обнулит верхние 3 байта и поместит 1 в младший байт. Команда movb просто изменит младший байт.

7
ответ дан 29 November 2019 в 22:50
поделиться

% eax - 32-битный регистр. Чтобы использовать меньшую ширину, вам понадобится % ax для 16 бит. % ax можно дополнительно разделить на % ah для старшего байта % ax и % al для младшего байта. То же самое и с другими GPR x86.

Глядя на ссылку на набор инструкций Intel для инструкции mov , я не вижу варианта, который мог бы переместить один байт в 32-битный регистр - - вероятно, это интерпретируется как переход в % al .

Поскольку movl является 32-битной инструкцией, значения для старших байтов будут соответствовать нулям в случай немедленного значения . Если бы вы двигались по памяти, вы бы переместили все 32-битное слово.

% eax не обнуляется, если вы не movl $ 0,% eax , или если вы xorl% eax,% eax . В противном случае он содержит то значение, которое было там ранее. Когда вы movl $ 1,% eax , вы получите 0x00000001 в регистре, потому что 32-битная инструкция перемещает 32-битное непосредственное значение в регистр.

5
ответ дан 29 November 2019 в 22:50
поделиться

long изначально было 32 бита, тогда как int и short были 16. И имена кодов операций не меняются каждый раз. кто-то выпускает новую операционную систему.

4
ответ дан 29 November 2019 в 22:50
поделиться

Второй вариант просто вызовет ошибку, x86 не имеет этой инструкции. X86 немного уникален в отношении загрузки байтов в определенные регистры. Да, в большинстве архитектур с набором команд операнд равен нулю или имеет знаковое расширение, но x86 позволяет вам записывать только младший байт или младшие 16 бит некоторых из них.

Конечно, есть и другие варианты, такие как очистка регистра, а затем увеличивая его, но вот три изначально разумно выглядящих варианта, которые у вас есть:

   0:   b8 01 00 00 00          movl   $0x1,%eax

   5:   31 c0                   xorl   %eax,%eax
   7:   b0 01                   movb   $0x1,%al

   9:   b0 01                   movb   $0x1,%al
   b:   0f b6 c0                movzbl %al,%eax

Первый - 5 байтов, второй - 4, третий - 5. Таким образом, второй - лучший выбор при оптимизации по пространству, в противном случае я полагаю, что самый скорее всего, будет быстро бежать - это первый. В наши дни X86 имеет глубокую конвейерную обработку, поэтому две инструкции будут блокироваться, и машине может потребоваться довольно много состояний ожидания в зависимости от деталей оборудования конвейера.

Конечно, эти операции x86 транслируются специфичными для ЦП способами в микрооперации ЦП , и так что кто знает, что произойдет.

3
ответ дан 29 November 2019 в 22:50
поделиться

% eax - 32 бита на 32-битных машинах. % ax составляет 16 бит, а % ah и % al - это его 8-битные старшие и младшие составляющие.

Следовательно, movl здесь совершенно справедливо. С точки зрения эффективности movl будет таким же быстрым, как movb , и обнуление старших 3 байтов % eax часто является желательным свойством. Возможно, позже вы захотите использовать его как 32-битное значение, поэтому movb не лучший способ переместить туда байт.

2
ответ дан 29 November 2019 в 22:50
поделиться
Другие вопросы по тегам:

Похожие вопросы: