常见的子表达式消除OpenCL

时间:2013-09-20 17:23:09

标签: opencl nvidia compiler-optimization

我有一个非常大的内核,它使用~1000个临时变量来计算~1000个方程。因此可以安全地假设所有临时变量都将放在私有的片外存储器中,即CUDA __本地存储器(我知道它很糟糕,但没有别的办法)。

我的问题是,如果在相邻行之间消除了常见的子表达式,如下所示:

const float t747 = t472*t28*t26*t715*t30*t11;
const float t748 = t472*t28*t717*t26*t30*t11;

正如您所看到的,唯一的区别是变量t717与t715。问题是这两行是否转化为7或12个全局负载?

因为如果目标编译器(在我的情况下是Nvidia Kepler GPU)不使用寄存器来缓存行之间的公共子表达式,我将需要自己实现它。

注意:所有代码都是自动生成的,因此无法进行手动调整。

编辑:所有t0-t999变量都声明为“const float”。

1 个答案:

答案 0 :(得分:0)

编译器将所有全局读取转换为直接读取。因此,在您的情况下 12 读取。

这是因为全局内存被视为易失性内存,并且无法进行缓存。但是,如果你只是这样做:(我想你知道,但无论如何......)

const float temp = t472*t28*t26*t30*t11;
const float t747 = temp*t715;
const float t748 = temp*t717;

编译器会将其转换为7个全局读取。

注意:至少这对于旧的arquitectures是有效的,我不知道是否有一些新的编译器/ arquitecture可以巧妙地检测这些情况并优化它们。