Существует несколько способов встраивания констант в поток команд:
- с использованием непосредственных операндов
- при загрузке с ПК-относительных адресов
Так что, хотя нет способа сделать немедленную загрузку в регистр XMM
, можно выполнить относительную загрузку ПК (в 64-битной системе) из значения, хранящегося «прямо рядом» с код выполняется. Это создает что-то вроде:
.align 4
.val:
.long 0x12345678
.long 0x9abcdef0
.long 0xfedbca98
.long 0x76543210
func:
movdqa .val(%rip), %xmm0
При разборке:
0000000000000000 :
0: 78 56 34 12 f0 de bc 9a
8: 98 ca db fe 10 32 54 76
0000000000000010 :
10: 66 0f 6f 05 e8 ff ff movdqa -0x18(%rip),%xmm0 # 0
что является очень компактным , 23 байта.
Другие варианты - построить значение в стеке и снова загрузить его оттуда. В 32-битной x86, где у вас нет доступа к памяти, относящейся к %rip
, это можно сделать за 24 байта (при условии, что указатель стека выровнен при входе; в противном случае требуется загрузка без выравнивания):
00000000 :
0: 68 78 56 34 12 push $0x12345678
5: 68 f0 de bc 9a push $0x9abcdef0
a: 68 98 ca db fe push $0xfedbca98
f: 68 10 32 54 76 push $0x76543210
14: 66 0f 6f 04 24 movdqa (%esp),%xmm0
В 64-битном режиме (выравнивание стека указателем при входе в функцию там гарантируется ABI), что заняло бы 27 байт:
0000000000000000 :
0: 48 b8 f0 de bc 9a 78 56 34 12 movabs $0x123456789abcdef0,%rax
a: 50 push %rax
b: 48 b8 10 32 54 76 98 ba dc fe movabs $0xfedcba9876543210,%rax
15: 50 push %rax
16: 66 0f 6f 04 24 movdqa (%rsp),%xmm0
Если вы сравните любой из них с версией MOVLHPS
, вы заметите, что она самая длинная:
0000000000000000 :
0: 48 b8 f0 de bc 9a 78 56 34 12 movabs $0x123456789abcdef0,%rax
a: 66 48 0f 6e c0 movq %rax,%xmm0
f: 48 b8 10 32 54 76 98 ba dc fe movabs $0xfedcba9876543210,%rax
19: 66 48 0f 6e c8 movq %rax,%xmm1
1e: 0f 16 c1 movlhps %xmm1,%xmm0
при 33 байтах.
Другое преимущество загрузки непосредственно из памяти команд состоит в том, что movdqa
не зависит от чего-либо предыдущего. Скорее всего, первая версия, предоставленная @Paul R, самая быстрая, какую только можно получить.