Optimization intersectRaySphere x86 fpu asm例程-如何优化
喂,我有一些c程序:Optimization intersectRaySphere x86 fpu asm例程-如何优化,optimization,assembly,x86,fpu,Optimization,Assembly,X86,Fpu,喂,我有一些c程序: inline float intersectRaySphere(float3* rayO, float3* rayV, float3* sO, float sR) { static float3 Q; Q = sub(sO,rayO); float cc = dot(&Q,&Q); float v = dot(&Q,rayV); float d = sR*sR - (cc - v*v);
inline float intersectRaySphere(float3* rayO, float3* rayV, float3* sO, float sR)
{
static float3 Q;
Q = sub(sO,rayO);
float cc = dot(&Q,&Q);
float v = dot(&Q,rayV);
float d = sR*sR - (cc - v*v);
// If there was no intersection, return -1
if (d < 0.0) return (-1.0f);
// Return the distance to the [first] intersecting point
return (v - sqrt(d));
}
经过测试,工作正常,c例程大约需要150个周期
7年前的奔腾4),我的asm例程大约需要66个周期(*)-事实就是如此
很好的改进,但也许还可以改进一点
tnx
(*)我对随机输入的数据进行测试时没有太在意,所以
可能是“非交叉”原因-没有涉及sqrt我将替换此:
fstp st0
fstp st0
fstp st0
ftst
fwait
fnstsw ax
fwait
sahf
jc ?__001
据此:
fcompp
fstp st0
fldz
fcomip st0, st1
ja ?__001
fnstsw
速度不快,sahf
也不是很好,尤其是在P4上。如果您不能使用fcomi
(即如果它必须在P1或PMMX上工作),您仍然可以通过直接在ax
中测试一点来跳过sahf
。我将替换此:
fstp st0
fstp st0
fstp st0
ftst
fwait
fnstsw ax
fwait
sahf
jc ?__001
据此:
fcompp
fstp st0
fldz
fcomip st0, st1
ja ?__001
fnstsw
速度不快,sahf
也不是很好,尤其是在P4上。如果你不能使用fcomi
(即如果它必须在P1或PMMX上工作),你仍然可以跳过sahf
,直接在ax
中测试一点。似乎对1-2个周期略有改善,有时很难说,因为我在不同的运行中以某种方式得到了直接的结果,有时68例如有时65-与fpu上的“经典”规格化相同-有时90有时80:/(例如,我使用fld xyz fld xyz存储的初始版本为90,使用一个fld xyz改进,堆栈存储也为90,但当我测量初始值时,它变为80-有点奇怪)@Grungfightr ok,当然,这不会有多大帮助,但我会期望更多(可能是4到6个周期)。好吧,没关系-我的测量精度不是很高,我只想了解fpu的基本概念-我仍然相信可能存在更多的规则来选择这样的fpu代码-但没关系-总有一天l8ter会用avx购买新的处理器,并尝试在avx下重写最重要的部分,现在我想训练准备l8er;-)65是好的,(非常好)此外,当“正常化”只是普通的加法,不做真正的几何计算工作时,需要80(不要尝试使用复杂的invsqry(29)但是-可能会更快-也不要尝试sse版本)[虽然65可能是因为我使用这种数据测试它,在不发生交集并且不调用sqrt的情况下]顺便说一下,你不应该在随机数据上测试这个。我敢肯定,如果你一直在同一个真实数据上测试,这些数字会更有意义。它们可能太高了-65对于平方根来说实在太低了,在很大一部分时间里不会发生。似乎在1-2个周期有轻微的改善,有时很难说,因为我在不同的运行中有不同的结果,有时68例如有时65-与fpu上的“经典”规格化相同-有时90有时80:/(例如,我使用fld xyz fld xyz存储的初始版本为90,使用一个fld xyz改进,堆栈存储也为90,但当我测量初始值时,它变为80-有点奇怪)@Grungfightr ok,当然,这不会有多大帮助,但我会期望更多(可能是4到6个周期)。好吧,没关系-我的测量精度不是很高,我只想了解fpu的基本概念-我仍然相信可能存在更多的规则来选择这样的fpu代码-但没关系-总有一天l8ter会用avx购买新的处理器,并尝试在avx下重写最重要的部分,现在我想训练准备l8er;-)65是好的,(非常好)此外,当“正常化”只是普通的加法,不做真正的几何计算工作时,需要80(不要尝试使用复杂的invsqry(29)但是-可能会更快-也不要尝试sse版本)[虽然65可能是因为我使用这种数据测试它,在不发生交集并且不调用sqrt的情况下]顺便说一下,你不应该在随机数据上测试这个。我敢肯定,如果你一直在同一个真实数据上测试,这些数字会更有意义。它们可能也会更高——65对于平方根来说实在太低了,在很大一部分时间里不会发生。