On Wed, Jun 15, 2016 at 1:35 PM, Henri Verbeet hverbeet@gmail.com wrote:
On 13 June 2016 at 20:32, Józef Kucia joseph.kucia@gmail.com wrote:
This implementation has some issues, e.g. a generated GLSL shader will produce a compilation error when the immediate constant buffer contains an unsigned integer which represents NaN. Morever, from testing a similar implementation, it seems that some drivers don't handle shaders with huge arrays very well and such shaders perform poorly. My current impression is that we should implement immediate constant buffers using a uniform variable.
Which drivers are that? Using uniforms does have some advantages, but it also means the GLSL compiler potentially has less opportunities for optimisation. Perhaps that's ok if we can safely assume any such optimisations would have already been done by the HLSL compiler. There's also the consideration that accessing uniforms can potentially have higher latency than accessing immediate values, although I'm not aware of any hardware that supports arrays of immediate values, as opposed to single (vec4) values.
Switching from arrays to uniforms improved performance noticeably for Gauntlet on OS X and on Linux with Nvidia binary drivers.
Mesa seems to lower const arrays to uniforms anyway. However, we cannot declare these arrays as const when uintBitsToFloat is used (at least in GLSL 1.30), so we are at risk of spilling these arrays to scratch memory. An excerpt from a comment in the Mesa source code: "Lower constant arrays to uniform arrays. Some driver backends (such as i965 and nouveau) don't handle constant arrays gracefully, instead treating them as ordinary writable temporary arrays. Since arrays can be large, this often means spilling them to scratch memory, which usually involves a large number of instructions.".