2 Compute shaders, 1 glMemoryBarrier = OK?

877 views Asked by At

Setup(OpenGL ES 3.1 on android device):

Compute_shader_clear (in PROGRAM_A):

layout (local_size_x = 8, local_size_y = 8) in;
layout(rgba32f, binding=0) writeonly uniform mediump image2D write00;
void main() {
 ...
 imageStore(write00, pixel, vec4(0.0));
}

Compute_shader_main (in PROGRAM_B):

layout (local_size_x = 8, local_size_y = 8) in;
layout(rgba32f, binding=0) writeonly uniform mediump image2D write00;
void main() {
 ...
 imageStore(write00, pixel, final_color);
}

Both compute shaders are pointing at the same texture (Binding zero = image unit zero)

App calling code:

glUseProgram(PROGRAM_A);
glDispatchCompute(90, 160, 1);
glUseProgram(PROGRAM_B);
GLES31.glMemoryBarrier(GLES31.GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);
glDispatchCompute(3, 160, 1);
...

This setup seems to work without a problem, but is this interpretation correct? :

  1. The barrier is necessary because it is possible that both dispatch commands could be running at the same time.

  2. The barrier means that no imageStore will be executed in the second dispatch until ALL imageStore calls in the first dispatch are finished.

1

There are 1 answers

1
Nicol Bolas On BEST ANSWER

The barrier is necessary because it is possible that both dispatch commands could be running at the same time.

Technically yes, but the more proper reason is "because the OpenGL ES specification says it is necessary."

The barrier means that no imageStore will be executed in the second dispatch until ALL imageStore calls in the first dispatch are finished.

What the barrier means is that, if there are read/write operations later that attempt to access data written previously, those read/write operations will read/overwrite data written by commands before the barrier.

How that gets implemented is an implementation detail. There could be hardware that could concurrently execute such commands, through the use of some ordering operation somehow. Granted, odds are good that most implementations will do what you said: wait until prior commands are executed and clear caches before executing subsequent commands.