Инструкция SSE2 для загрузки целых чисел в обратном порядке

Есть ли инструкция SSE2 для загрузки 128-битного векторного регистра int из буфера int в обратном порядке?


person Andy    schedule 16.05.2013    source источник


Ответы (2)


32-битные элементы int после обычной загрузки довольно просто перевернуть:

__m128i v = _mm_load_si128(buff);                    // MOVDQA
v = _mm_shuffle_epi32(v, _MM_SHUFFLE(0, 1, 2, 3));   // PSHUFD  - mask = 00 01 10 11 = 0x1b

Вы можете сделать то же самое для 16-битных элементов short, но для этого потребуется больше инструкций:

__m128i v = _mm_load_si128(buff);                    // MOVDQA
v = _mm_shuffle_epi32(v, _MM_SHUFFLE(0, 1, 2, 3));   // PSHUFD  - mask = 00 01 10 11 = 0x1b
v = _mm_shufflelo_epi16(v, _MM_SHUFFLE(2, 3, 0, 1)); // PSHUFLW - mask = 10 11 00 01 = 0xb1
v = _mm_shufflehi_epi16(v, _MM_SHUFFLE(2, 3, 0, 1)); // PSHUFHW - mask = 10 11 00 01 = 0xb1

Обратите внимание, что вы можете сделать это с меньшим количеством инструкций, используя _mm_shuffle_epi8 (PSHUFB)< /a>, если доступен SSSE3:

const __m128i vm = _mm_setr_epi8(14, 15, 12, 13, 10, 11, 8, 9, 6, 7, 4, 5, 2, 3, 0, 1);
                                     // initialise vector mask for use with PSHUFB
                                     // NB: do this once, outside any processing loop
...
__m128i v = _mm_load_si128(buff);    // MOVDQA
v = _mm_shuffle_epi8(v, vm);         // PSHUFB
person Paul R    schedule 16.05.2013
comment
Спасибо, Пол. Ваша логика работает нормально. Но я не мог понять использование второго параметра 0x1B. Это какая-то маска? Другое сомнение..Можно ли сделать такую ​​же операцию на шортах? - person Andy; 16.05.2013
comment
Я добавил второй пример загрузки и переворота шорт. Маска описана в документации Intel, но я добавил комментарии, чтобы показать, как она устроена. - person Paul R; 16.05.2013
comment
P.S. Я настоятельно рекомендую загрузить Руководство по Intel Intrinsics — очень полезное инструмент для WIN/Mac OS X/Linux, который документирует все инструкции и встроенные функции SSE/AVX в очень доступной форме. - person Paul R; 16.05.2013
comment
Я бы использовал PSHUFB для обращения вектора коротких позиций, если только SSSE3 недоступен. - person Stephen Canon; 21.05.2013
comment
Конечно, но ОП специально просил решения SSE2. Я добавлю примечание к ответу. - person Paul R; 21.05.2013
comment
Поддерживаются SSE3, SSSE3, SSE4.1 и SSE4.2. Что касается использования _mm_shuffle_epi8 (PSHUFB), я не совсем могу понять, как использовать маску. Может кто-нибудь объяснить? - person Andy; 27.05.2013
comment
ОК. Я добавил пример PSHUFB выше для изменения порядка 16-битных целых чисел в векторе. - person Paul R; 27.05.2013
comment
Спасибо. Теперь мне кажется, что _mm_shuffle_epi8 имеет смысл. Я новичок во внутреннем программировании Intel (хотя я работал с внутренними компонентами NEON), и изначально мне казалось, что в SSE нет простых инструкций для выполнения определенных функций. Но теперь похоже, что большинство операций возможно с помощью предоставленных наборов инструкций вместе. с правильной логикой :-) - person Andy; 27.05.2013
comment
Да, это правда — есть довольно много приемов, которым нужно научиться, чтобы извлечь максимальную пользу из SIMD в целом и SSE в частности. - person Paul R; 27.05.2013
comment
@ Пол ... Есть ли какие-либо учебные пособия или документы, которые также могут помочь мне в изучении нескольких приемов торговли. Пожалуйста, предложите. - person Andy; 28.05.2013
comment
К сожалению, там не так много - лучшее, что вы можете сделать, это прочитать и понять любой существующий код, который вы можете найти, например. в кодовых базах с открытым исходным кодом, а также, конечно, путем написания собственных оптимизированных подпрограмм SIMD. - person Paul R; 28.05.2013

РЕДАКТИРОВАТЬ: (следующее предназначено для скаляров с плавающей запятой одинарной точности, оставив его здесь на всякий случай)

Самый приблизительный (и удобный) — _mm_loadr_ps встроенный. Имейте в виду, что адрес должен быть выровнен по 16 байтам.

Хотя эта встроенная функция переводится как больше, чем инструкция (MOVAPS + перетасовка).

person Trax    schedule 16.05.2013
comment
Спасибо за ответ, но эта инструкция загружает четыре значения с плавающей запятой одинарной точности в обратном порядке. Я ищу ту же операцию для целых чисел, но я думаю, что это не поддерживается. - person Andy; 16.05.2013
comment
Да, я не заметил, что вы говорили о целочисленных значениях (должен был перечитать ваш заголовок). Ответ Пола Р - это то, что вам нужно. - person Trax; 16.05.2013
comment
Да. Просто любопытно, можно ли выполнить ту же операцию с короткими значениями? - person Andy; 16.05.2013