2017-12-27 773 views
0

我们通常使用常量在C++中暗示值没有改变(只读),在他们选择的着色器或资源定义为什么在GLSL/VK字制服? Wodn`t更加一致,并使用从C/C++福尔康着色器和资源:为什么统一,而不是常量资源

借来的关键字旁边,可能在着色器定义了统一的关键字提供线索编译器对这些资源的附加为接近硬件越好,大概共享内存寄存器?不确定。

这也可能是为什么他们在VkSpec中提到。我们需要少量的这些资源类型的数据。就像例如:宇宙常数的值..等

是我遗失的东西,还是一些过去的历史?

回答

2

GPU编程中的制服和C++中的const都集中在不同的事情上。

C++ const记录了一个变量不打算被改变,并且执行了一些编译器。因此,更重要的是使用类型系统来提高清晰度并强制实现预期用途 - 这对于大型项目软件工程很重要。你仍然可以用const_cast或其他技巧绕过它,编译器不能假设你没有,所以它不是严格执行。

制服的重要之处在于它们是统一的。这意味着只要他们在平局中被读取,它们就具有相同的值。由于在单次绘图调用中可能会有数百到数百万次的该值读取,因此可以将其缓存起来,并且只需将其一个副本缓存起来,或者可以在着色器运行之前将其预加载到寄存器(或缓存)中,它可以缓存在非连贯的缓存中,单个读取结果可以在核心中的所有SIMD通道上广播等。为此,内容不能改变的事实必须严格执行(与内存别名你可以解决这个问题,现在,但结果是非常不确定的,如果你这样做)。如此统一的真正意义不在于向其他程序员声明软件工程的好处,如const,它是向编译器和驱动程序声明意图,以便它们可以基于它进行优化。

D3D使用“常量”和“常量缓冲区”而不是统一的,所以很明显存在一些重叠。尽管这样做的确会导致像“每次更新常量多少次?”这样的说法。当你想到这件事时,这是一种奇怪的事情:)。这些值在着色器代码中是恒定的,但在API级别上非常不稳定。

2

这个词的词源在这里很重要。术语“统一”来源于GLSL,它受Renderman标准着色器术语的启发。 In Renderman,“统一”用于“其值在表面的任何部分开始阴影处恒定”的值。这是“变化”的替代方法,它表示在表面上插值的值。

“常量”意味着值从来没有的变化。统一的价值确实发生了变化他们根本不会像其他值那样改变频率。输入值每次调用更改,统一值更改每次绘制调用,常量值不更改。请注意,在GLSL中,const通常意味着“编译时常量”:编译时设置的值,永远不会更改。

Vulkan中的统一变量最终来自存在于着色器之外的资源。由缓冲区馈送的统一变量块,由常量状态馈送的常量中的统一都是由用户设置的外部资源。这与编译时常量struct有个根本不同的概念。

由于它与常量结构不同,它需要一个不同的术语来请求它。