我一直在努力弄清楚如何在非常关键的几行代码中获得一些改进:
float x = a*b;
float y = c*d;
float z = e*f;
float w = g*h;
所有 a, b, c... 都是 float 。
我决定研究使用 SSE,但似乎找不到任何改进,事实上它的速度是原来的两倍。我的 SSE 代码是:
Vector4 abcd, efgh, result;
abcd = [float a, float b, float c, float d];
efgh = [float e, float f, float g, float h];
_asm {
movups xmm1, abcd
movups xmm2, efgh
mulps xmm1, xmm2
movups result, xmm1
}
我也尝试过使用标准内联汇编,但似乎我无法像使用 SSE 那样将寄存器与四个浮点一起打包。
任何评论或帮助将不胜感激,我主要需要了解为什么我使用 SSE 的计算比串行 C++ 代码慢?
我在 Visual Studio 2005 中编译,在 Windows XP 上,使用带有 HT 的 Pentium 4,如果它提供任何额外的信息来协助。
提前致谢!
最佳答案
正如您所发现的,仅用 SSE 替换几条指令是行不通的,因为您需要在内存中随机移动数据才能正确加载 SSE 寄存器,并且这会在内存中移动数据 (构建数组的位)会降低你的性能,因为内存非常慢(除了硬盘,这些天内存总是瓶颈)。
此外,如果不先写入 RAM 再读取,就无法在 SSE 和 FPU/ALU 之间移动数据。现代 IA32 芯片可以很好地应对这种特定模式(先写后读),但仍会使某些缓存无效,这会产生链式 react 。
要充分利用 SSE,您需要查看整个算法和算法使用的数据。 a、b、c 和 d 以及 e、f、g 和 h 的值需要永久保存在这些数组中,以便在加载 SSE 寄存器之前不会在内存中移动数据。这并不简单,可能需要对代码和数据进行大量修改(您可能需要在磁盘上以不同方式存储数据)。
可能还值得指出的是,SSE 仅为 32 位(如果使用 double ,则为 64 位),而 FPU 为 80 位(无论 float 还是 double ),因此与使用 FPU 相比,使用 SSE 时得到的结果略有不同.只有您知道这是否会成为问题。
关于c++ - 帮助组装/SSE 乘法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2961504/