我如何使用SSE执行8 × 8矩阵操作

How do I perform 8 x 8 matrix operation using SSE?

本文关键字:操作 执行 何使用 SSE      更新时间:2023-10-16

我最初的尝试是这样的(假设我们想要相乘)

  __m128 mat[n]; /* rows */
  __m128 vec[n] = {1,1,1,1};
  float outvector[n];
   for (int row=0;row<n;row++) {
       for(int k =3; k < 8; k = k+ 4)
       {
           __m128 mrow = mat[k];
           __m128 v = vec[row];
           __m128 sum = _mm_mul_ps(mrow,v);
           sum= _mm_hadd_ps(sum,sum); /* adds adjacent-two floats */
       }
           _mm_store_ss(&outvector[row],_mm_hadd_ps(sum,sum));
 }

但这显然不起作用。我该怎么做呢?

我应该一次加载4个....

另一个问题是:如果我的数组非常大(比如n = 1000),我怎么能使它16字节对齐?这可能吗?

OK…我将使用行矩阵约定。[m]的每一行需要(2)__m128个元素来产生8个浮点数。8x1向量v是列向量。由于您使用的是haddps指令,我假设SSE3是可用的。查找r = [m] * v:

void mul (__m128 r[2], const __m128 m[8][2], const __m128 v[2])
{
    __m128 t0, t1, t2, t3, r0, r1, r2, r3;
    t0 = _mm_mul_ps(m[0][0], v[0]);
    t1 = _mm_mul_ps(m[1][0], v[0]);
    t2 = _mm_mul_ps(m[2][0], v[0]);
    t3 = _mm_mul_ps(m[3][0], v[0]);
    t0 = _mm_hadd_ps(t0, t1);
    t2 = _mm_hadd_ps(t2, t3);
    r0 = _mm_hadd_ps(t0, t2);
    t0 = _mm_mul_ps(m[0][1], v[1]);
    t1 = _mm_mul_ps(m[1][1], v[1]);
    t2 = _mm_mul_ps(m[2][1], v[1]);
    t3 = _mm_mul_ps(m[3][1], v[1]);
    t0 = _mm_hadd_ps(t0, t1);
    t2 = _mm_hadd_ps(t2, t3);
    r1 = _mm_hadd_ps(t0, t2);
    t0 = _mm_mul_ps(m[4][0], v[0]);
    t1 = _mm_mul_ps(m[5][0], v[0]);
    t2 = _mm_mul_ps(m[6][0], v[0]);
    t3 = _mm_mul_ps(m[7][0], v[0]);
    t0 = _mm_hadd_ps(t0, t1);
    t2 = _mm_hadd_ps(t2, t3);
    r2 = _mm_hadd_ps(t0, t2);
    t0 = _mm_mul_ps(m[4][1], v[1]);
    t1 = _mm_mul_ps(m[5][1], v[1]);
    t2 = _mm_mul_ps(m[6][1], v[1]);
    t3 = _mm_mul_ps(m[7][1], v[1]);
    t0 = _mm_hadd_ps(t0, t1);
    t2 = _mm_hadd_ps(t2, t3);
    r3 = _mm_hadd_ps(t0, t2);
    r[0] = _mm_add_ps(r0, r1);
    r[1] = _mm_add_ps(r2, r3);
}

至于对齐,__m128类型的变量应该在堆栈上自动对齐。对于动态内存,这不是一个安全的假设。一些malloc/new实现可能只返回保证为8字节对齐的内存。

intrinsics头文件提供了_mm_malloc和_mm_free。在本例中,align参数应为(16)。

Intel开发了一个小矩阵库,用于大小范围从1×1到6×6的矩阵。应用说明AP-930流SIMD扩展-矩阵乘法详细描述了乘法两个6×6矩阵的算法。这应该可以适应其他大小的矩阵。