Наиболее эффективный способ хранения 4 точечных произведений в непрерывном массиве на C с использованием встроенных функций SSE

Я оптимизирую некоторый код для микроархитектуры Intel x86 Nehalem с использованием встроенных функций SSE.

Часть моей программы вычисляет 4 точечных произведения и добавляет каждый результат к предыдущим значениям в непрерывном фрагменте массива. В частности,

tmp0 = _mm_dp_ps(A_0m, B_0m, 0xF1);
tmp1 = _mm_dp_ps(A_1m, B_0m, 0xF2);
tmp2 = _mm_dp_ps(A_2m, B_0m, 0xF4);
tmp3 = _mm_dp_ps(A_3m, B_0m, 0xF8);

tmp0 = _mm_add_ps(tmp0, tmp1);
tmp0 = _mm_add_ps(tmp0, tmp2);
tmp0 = _mm_add_ps(tmp0, tmp3);
tmp0 = _mm_add_ps(tmp0, C_0n);

_mm_storeu_ps(C_2, tmp0);

Обратите внимание, что я собираюсь сделать это, используя 4 временных регистра xmm для хранения результата каждого скалярного произведения. В каждом регистре xmm результат помещается в уникальные 32 бита относительно других временных регистров xmm, так что конечный результат выглядит следующим образом:

tmp0 = R0-zero-zero-zero

tmp1 = zero-R1 -ноль-ноль

tmp2 = ноль-ноль-R2-ноль

tmp3 = ноль-ноль-ноль-R3

Я объединяю значения, содержащиеся в каждой переменной tmp, в одну переменную xmm, суммируя их с следующие инструкции:

tmp0 = _mm_add_ps(tmp0, tmp1);
tmp0 = _mm_add_ps(tmp0, tmp2);
tmp0 = _mm_add_ps(tmp0, tmp3);

Наконец, Я добавляю регистр, содержащий все 4 результата скалярных произведений, в непрерывную часть массива, чтобы индексы массива увеличивались скалярным произведением, например (C_0n - это 4 значения, которые в настоящее время находятся в массиве, который должен быть обновлен; C_2 является адресом, указывающим на эти 4 значения):

tmp0 = _mm_add_ps(tmp0, C_0n);
_mm_storeu_ps(C_2, tmp0);

Я хочу знать, есть ли более эффективный способ получить результаты скалярных произведений и добавить их в непрерывный кусок массива. Таким образом, я делаю 3 добавления между регистрами, в которых есть только одно ненулевое значение. Похоже, должен быть более эффективный способ сделать это.

Я ценю любую помощь. Спасибо.

11
задан Paul R 14 November 2010 в 07:35
поделиться