有没有办法在Vulkan SPIR-V中使用OpenCL C mad函数?

时间:2019-06-24 08:31:18

标签: glsl opencl vulkan fma

我们知道,至少有两种方法来计算a * b + c

  1. ret := a*b; ret := ret + c;

  2. ret := fma(a, b, c);

但是在OpenCL C中,还有第三个函数“ mad”,它将精度与性能进行了权衡。

在LunarG sdk中,默认的SPIR-V编译器将编译GLSL和HLSL着色语言,并且GLSL规范v4.60中未提及“ mad”功能。

如何在Vulkan中使用“疯狂”功能?

1 个答案:

答案 0 :(得分:2)

这里有些误会。

融合乘法加法并不意味着精度降低。由于在操作步骤之间保持内部硬件精度差异,因此与使用乘法然后加上与fma相比,该数字可能略有不同。因此,在某些API /语言中,默认情况下未启用自动FMA,只有在编译器中使用了快速运算符或特定标志时,才会启用FMA。可能在某些系统中精度会降低,但这并不是它的含义。

但是,在SPIR-V中,虽然似乎没有针对FMA的特定说明,但规范明确预测并允许在SPIR-V-> gpu汇编编译之后进行。它甚至在语言中带有NoContraction装饰。

  

无约束   适用于算术指令以指示   操作不能与另一条指令结合形成一个指令   操作。 例如,如果将其应用于OpFMul,则该乘法不能   与加法结合使用以产生融合的乘法加法运算。   此外,不允许此类操作重新关联;例如。,   add(a + add(b + c))无法转换为add(add(a + b)+ c)。

请注意,SPIR-V并不是着色器的全部。它只是着色器的可移植中间表示,然后由供应商vulkan驱动程序进一步编译。没有机器直接运行SPIR-V。这类优化留给驱动程序执行,而不是由程序员执行。您通常可以假设这样的优化将在适当的条件下发生,这对于缺少显式FMA内置功能的其他编程语言是相同的。