"Оптимизация для PENTIUM процессора" - читать интересную книгу автора

NEG EAX
MOV [EDI+4*ECX], EAX
INC ECX ; выравниваем счетчик
JZ SHORT L2 ; N = 1
L1: MOV EAX, [ESI+4*ECX] ; u
MOV EBX, [ESI+4*ECX+4] ; v (спаривание)
NEG EAX ; u
NEG EBX ; u
MOV [EDI+4*ECX], EAX ; u
MOV [EDI+4*ECX+4], EBX ; v (спаривание)
ADD ECX, 2 ; u
JNZ L1 ; v (спаривание)
L2:

Мы делаем две операции параллельно, достигая лучшего спаривания. Мы проверяем
N на нечетность и если это так, то выполняем одну операцию за пределами цикла,
поскольку цикл теперь может выполнить только четное количество операций.

У цикла есть остановка AGI в первой инструкции MOV, поскольку ECX был изменен
в предыдущем такте цикла. У цикла уходит 6 тактов на две операции.

Реорганизация цикла, для удаления остановки AGI
-----------------------------------------------
Пример 8:

MOV ESI, [A]
MOV EAX, [N]
MOV EDI, [B]
XOR ECX, ECX
LEA ESI, [ESI+4*EAX] ; указатель на конец массива A
SUB ECX, EAX ; -N
LEA EDI, [EDI+4*EAX] ; указатель на конец массива B
JZ SHORT L3
TEST AL,1 ; тест на нечетность N
JZ L2
MOV EAX, [ESI+4*ECX] ; N - нечетное. делаем четным
NEG EAX ; нет возможности спариться
MOV [EDI+4*ECX-4], EAX
INC ECX ; выравниваем счетчик
JNZ L2
NOP ; добавляем NOPы если JNZ L2 не
NOP ; предсказан.
JMP L3 ; N = 1
L1: NEG EAX ; u
NEG EBX ; u
MOV [EDI+4*ECX-8], EAX ; u
MOV [EDI+4*ECX-4], EBX ; v (спаривание)
L2: MOV EAX, [ESI+4*ECX] ; u
MOV EBX, [ESI+4*ECX+4] ; v (спаривание)
ADD ECX, 2 ; u