<p><code>glMemoryBarrier</code> is for when you want to make <a href="https://www.khronos.org/opengl/wiki/Memory_Model#Incoherent_memory_access" rel="nofollow noreferrer">writes from one rendering command visible to reads from a subsequent rendering command</a>.</p>

<p>That is, you can do all the atomics you like during a rendering command. But without the barrier, there's no guarantee that any of those atomic actions will be visible to later commands. Yes, they will still be <em>atomic</em>, but this only ensures that they will each execute in some order and each operation will fully execute before the next. What they won't ensure is that operations which OpenGL defines has happening "later" will execute before earlier operations.</p>

<p>Sometimes, you actually don't care about the order of the operations; being atomic may be enough. And sometimes, you <em>do care</em>.</p>

<p>Consider the case of a "linked-list" style blending buffer. Each pixel in the image is an integer that represents one of the items in the list. Each FS invocation will use an atomic increment to get a unique identifier, then swap that identifier with the current value in the image. It writes its pixel data to the entry in an SSBO, along with the identifier it swapped out of the image.</p>

<p>When doing that atomic increment on the unique identifier, you don't care if FS invocations from two different rendering commands execute out of order. You simply need the operation to be atomic. Similarly, the swap doesn't have to be in order; it just needs to be atomic. As long as they all execute, and the atomic operations do their jobs, then they will be fine.</p>

<p>Now, when it comes time to do blending based on this data, <em>that</em> is when you need to be able to read all of the data that was previously written. And that rendering operation requires <code>glMemoryBarrier</code>.</p>

<p>Of course, you're not necessarily using atomic operations to <em>read</em> these values.</p>

CC BY-SA 3.0
2017-09-02T22:31:26.180Z
2017-11-12T02:31:07.540Z
2017-11-12T02:31:07.540Z
Nicol Bolas
<p>I am reading the OpenGL SuperBible 7th edition which covers <em>atomic operations</em> on memory specifically within shader storage blocks.</p>

<p>It says (about atomic operations):</p>

<blockquote>
  <p>If two invocations access the same memory locations... then they will be <em>serialized</em> and only one will get to go at one time.</p>
</blockquote>

<p>Great. However, it then goes on to cover <strong>Synchronizing Access to Memory</strong> specifically and the use of <code>glMemoryBarrier</code></p>

<p>As I understand it, you need to use <code>glMemoryBarrier</code> once you start writing to buffers from shaders.</p>

<p>However, the distinction is not made clear to me about <em>why</em> I need to use a barrier if the operations I am doing within my shader are atomic operations.</p>

<p>It's possible I am conflating atomic operations and general memory access, but, in the book the line is not clearly drawn.</p>

<p>When is it that a <code>glMemoryBarrier</code> is required? Is it <strong>everytime</strong> a shader writes to memory (whether the operations are atomic or not)?</p>

<opengl><memory><synchronization>
Why do I need memory barrier when doing atomic operations?
Startec
# Why do I need memory barrier when doing atomic operations?

(Asked by: username_0 on 2017-09-02)

I am reading the OpenGL SuperBible 7th edition which covers *atomic operations* on memory specifically within shader storage blocks.

It says (about atomic operations):

> If two invocations access the same memory locations... then they will be *serialized* and only one will get to go at one time.

Great. However, it then goes on to cover **Synchronizing Access to Memory** specifically and the use of `glMemoryBarrier`

As I understand it, you need to use `glMemoryBarrier` once you start writing to buffers from shaders.

However, the distinction is not made clear to me about *why* I need to use a barrier if the operations I am doing within my shader are atomic operations.

It's possible I am conflating atomic operations and general memory access, but, in the book the line is not clearly drawn.

When is it that a `glMemoryBarrier` is required? Is it **everytime** a shader writes to memory (whether the operations are atomic or not)?

**Tags:** opengl, memory, synchronization


---

## 1 answers

### Answer by username_1 on 2017-09-02. Score: 6 | Accepted answer

`glMemoryBarrier` is for when you want to make [writes from one rendering command visible to reads from a subsequent rendering command](https://www.khronos.org/opengl/wiki/Memory_Model#Incoherent_memory_access).

That is, you can do all the atomics you like during a rendering command. But without the barrier, there's no guarantee that any of those atomic actions will be visible to later commands. Yes, they will still be *atomic*, but this only ensures that they will each execute in some order and each operation will fully execute before the next. What they won't ensure is that operations which OpenGL defines has happening "later" will execute before earlier operations.

Sometimes, you actually don't care about the order of the operations; being atomic may be enough. And sometimes, you *do care*.

Consider the case of a "linked-list" style blending buffer. Each pixel in the image is an integer that represents one of the items in the list. Each FS invocation will use an atomic increment to get a unique identifier, then swap that identifier with the current value in the image. It writes its pixel data to the entry in an SSBO, along with the identifier it swapped out of the image.

When doing that atomic increment on the unique identifier, you don't care if FS invocations from two different rendering commands execute out of order. You simply need the operation to be atomic. Similarly, the swap doesn't have to be in order; it just needs to be atomic. As long as they all execute, and the atomic operations do their jobs, then they will be fine.

Now, when it comes time to do blending based on this data, *that* is when you need to be able to read all of the data that was previously written. And that rendering operation requires `glMemoryBarrier`.

Of course, you're not necessarily using atomic operations to *read* these values.


---

