1*61046927SAndroid Build Coastguard Worker /*
2*61046927SAndroid Build Coastguard Worker * Copyright © 2011 Marek Olšák <[email protected]>
3*61046927SAndroid Build Coastguard Worker *
4*61046927SAndroid Build Coastguard Worker * Permission is hereby granted, free of charge, to any person obtaining a
5*61046927SAndroid Build Coastguard Worker * copy of this software and associated documentation files (the "Software"),
6*61046927SAndroid Build Coastguard Worker * to deal in the Software without restriction, including without limitation
7*61046927SAndroid Build Coastguard Worker * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8*61046927SAndroid Build Coastguard Worker * and/or sell copies of the Software, and to permit persons to whom the
9*61046927SAndroid Build Coastguard Worker * Software is furnished to do so, subject to the following conditions:
10*61046927SAndroid Build Coastguard Worker *
11*61046927SAndroid Build Coastguard Worker * The above copyright notice and this permission notice (including the next
12*61046927SAndroid Build Coastguard Worker * paragraph) shall be included in all copies or substantial portions of the
13*61046927SAndroid Build Coastguard Worker * Software.
14*61046927SAndroid Build Coastguard Worker *
15*61046927SAndroid Build Coastguard Worker * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16*61046927SAndroid Build Coastguard Worker * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17*61046927SAndroid Build Coastguard Worker * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18*61046927SAndroid Build Coastguard Worker * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19*61046927SAndroid Build Coastguard Worker * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20*61046927SAndroid Build Coastguard Worker * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21*61046927SAndroid Build Coastguard Worker * DEALINGS IN THE SOFTWARE.
22*61046927SAndroid Build Coastguard Worker */
23*61046927SAndroid Build Coastguard Worker
24*61046927SAndroid Build Coastguard Worker /**
25*61046927SAndroid Build Coastguard Worker * \file barrier.c
26*61046927SAndroid Build Coastguard Worker * Implementation of various pipeline barrier entry points.
27*61046927SAndroid Build Coastguard Worker *
28*61046927SAndroid Build Coastguard Worker * \author Marek Olšák <[email protected]>
29*61046927SAndroid Build Coastguard Worker */
30*61046927SAndroid Build Coastguard Worker
31*61046927SAndroid Build Coastguard Worker #include "context.h"
32*61046927SAndroid Build Coastguard Worker #include "api_exec_decl.h"
33*61046927SAndroid Build Coastguard Worker
34*61046927SAndroid Build Coastguard Worker #include "pipe/p_context.h"
35*61046927SAndroid Build Coastguard Worker
36*61046927SAndroid Build Coastguard Worker
37*61046927SAndroid Build Coastguard Worker static void
memory_barrier(struct gl_context * ctx,GLbitfield barriers)38*61046927SAndroid Build Coastguard Worker memory_barrier(struct gl_context *ctx, GLbitfield barriers)
39*61046927SAndroid Build Coastguard Worker {
40*61046927SAndroid Build Coastguard Worker struct pipe_context *pipe = ctx->pipe;
41*61046927SAndroid Build Coastguard Worker unsigned flags = 0;
42*61046927SAndroid Build Coastguard Worker
43*61046927SAndroid Build Coastguard Worker if (barriers & GL_VERTEX_ATTRIB_ARRAY_BARRIER_BIT)
44*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_VERTEX_BUFFER;
45*61046927SAndroid Build Coastguard Worker if (barriers & GL_ELEMENT_ARRAY_BARRIER_BIT)
46*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_INDEX_BUFFER;
47*61046927SAndroid Build Coastguard Worker if (barriers & GL_UNIFORM_BARRIER_BIT)
48*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_CONSTANT_BUFFER;
49*61046927SAndroid Build Coastguard Worker if (barriers & GL_TEXTURE_FETCH_BARRIER_BIT)
50*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_TEXTURE;
51*61046927SAndroid Build Coastguard Worker if (barriers & GL_SHADER_IMAGE_ACCESS_BARRIER_BIT)
52*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_IMAGE;
53*61046927SAndroid Build Coastguard Worker if (barriers & GL_COMMAND_BARRIER_BIT)
54*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_INDIRECT_BUFFER;
55*61046927SAndroid Build Coastguard Worker if (barriers & GL_PIXEL_BUFFER_BARRIER_BIT) {
56*61046927SAndroid Build Coastguard Worker /* The PBO may be
57*61046927SAndroid Build Coastguard Worker * (1) bound as a texture for PBO uploads, or
58*61046927SAndroid Build Coastguard Worker * (2) accessed by the CPU via transfer ops.
59*61046927SAndroid Build Coastguard Worker * For case (2), we assume automatic flushing by the driver.
60*61046927SAndroid Build Coastguard Worker */
61*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_TEXTURE;
62*61046927SAndroid Build Coastguard Worker }
63*61046927SAndroid Build Coastguard Worker if (barriers & GL_TEXTURE_UPDATE_BARRIER_BIT) {
64*61046927SAndroid Build Coastguard Worker /* GL_TEXTURE_UPDATE_BARRIER_BIT:
65*61046927SAndroid Build Coastguard Worker * Texture updates translate to:
66*61046927SAndroid Build Coastguard Worker * (1) texture transfers to/from the CPU,
67*61046927SAndroid Build Coastguard Worker * (2) texture as blit destination, or
68*61046927SAndroid Build Coastguard Worker * (3) texture as framebuffer.
69*61046927SAndroid Build Coastguard Worker * Some drivers may handle these automatically, and can ignore the bit.
70*61046927SAndroid Build Coastguard Worker */
71*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_UPDATE_TEXTURE;
72*61046927SAndroid Build Coastguard Worker }
73*61046927SAndroid Build Coastguard Worker if (barriers & GL_BUFFER_UPDATE_BARRIER_BIT) {
74*61046927SAndroid Build Coastguard Worker /* GL_BUFFER_UPDATE_BARRIER_BIT:
75*61046927SAndroid Build Coastguard Worker * Buffer updates translate to
76*61046927SAndroid Build Coastguard Worker * (1) buffer transfers to/from the CPU,
77*61046927SAndroid Build Coastguard Worker * (2) resource copies and clears.
78*61046927SAndroid Build Coastguard Worker * Some drivers may handle these automatically, and can ignore the bit.
79*61046927SAndroid Build Coastguard Worker */
80*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_UPDATE_BUFFER;
81*61046927SAndroid Build Coastguard Worker }
82*61046927SAndroid Build Coastguard Worker if (barriers & GL_CLIENT_MAPPED_BUFFER_BARRIER_BIT)
83*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_MAPPED_BUFFER;
84*61046927SAndroid Build Coastguard Worker if (barriers & GL_QUERY_BUFFER_BARRIER_BIT)
85*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_QUERY_BUFFER;
86*61046927SAndroid Build Coastguard Worker if (barriers & GL_FRAMEBUFFER_BARRIER_BIT)
87*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_FRAMEBUFFER;
88*61046927SAndroid Build Coastguard Worker if (barriers & GL_TRANSFORM_FEEDBACK_BARRIER_BIT)
89*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_STREAMOUT_BUFFER;
90*61046927SAndroid Build Coastguard Worker if (barriers & GL_ATOMIC_COUNTER_BARRIER_BIT)
91*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_SHADER_BUFFER;
92*61046927SAndroid Build Coastguard Worker if (barriers & GL_SHADER_STORAGE_BARRIER_BIT)
93*61046927SAndroid Build Coastguard Worker flags |= PIPE_BARRIER_SHADER_BUFFER;
94*61046927SAndroid Build Coastguard Worker
95*61046927SAndroid Build Coastguard Worker if (flags && pipe->memory_barrier)
96*61046927SAndroid Build Coastguard Worker pipe->memory_barrier(pipe, flags);
97*61046927SAndroid Build Coastguard Worker }
98*61046927SAndroid Build Coastguard Worker
99*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_TextureBarrierNV(void)100*61046927SAndroid Build Coastguard Worker _mesa_TextureBarrierNV(void)
101*61046927SAndroid Build Coastguard Worker {
102*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
103*61046927SAndroid Build Coastguard Worker
104*61046927SAndroid Build Coastguard Worker if (!ctx->Extensions.NV_texture_barrier) {
105*61046927SAndroid Build Coastguard Worker _mesa_error(ctx, GL_INVALID_OPERATION,
106*61046927SAndroid Build Coastguard Worker "glTextureBarrier(not supported)");
107*61046927SAndroid Build Coastguard Worker return;
108*61046927SAndroid Build Coastguard Worker }
109*61046927SAndroid Build Coastguard Worker
110*61046927SAndroid Build Coastguard Worker ctx->pipe->texture_barrier(ctx->pipe, PIPE_TEXTURE_BARRIER_SAMPLER);
111*61046927SAndroid Build Coastguard Worker }
112*61046927SAndroid Build Coastguard Worker
113*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_MemoryBarrier(GLbitfield barriers)114*61046927SAndroid Build Coastguard Worker _mesa_MemoryBarrier(GLbitfield barriers)
115*61046927SAndroid Build Coastguard Worker {
116*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
117*61046927SAndroid Build Coastguard Worker
118*61046927SAndroid Build Coastguard Worker memory_barrier(ctx, barriers);
119*61046927SAndroid Build Coastguard Worker }
120*61046927SAndroid Build Coastguard Worker
121*61046927SAndroid Build Coastguard Worker static ALWAYS_INLINE void
memory_barrier_by_region(struct gl_context * ctx,GLbitfield barriers,bool no_error)122*61046927SAndroid Build Coastguard Worker memory_barrier_by_region(struct gl_context *ctx, GLbitfield barriers,
123*61046927SAndroid Build Coastguard Worker bool no_error)
124*61046927SAndroid Build Coastguard Worker {
125*61046927SAndroid Build Coastguard Worker GLbitfield all_allowed_bits = GL_ATOMIC_COUNTER_BARRIER_BIT |
126*61046927SAndroid Build Coastguard Worker GL_FRAMEBUFFER_BARRIER_BIT |
127*61046927SAndroid Build Coastguard Worker GL_SHADER_IMAGE_ACCESS_BARRIER_BIT |
128*61046927SAndroid Build Coastguard Worker GL_SHADER_STORAGE_BARRIER_BIT |
129*61046927SAndroid Build Coastguard Worker GL_TEXTURE_FETCH_BARRIER_BIT |
130*61046927SAndroid Build Coastguard Worker GL_UNIFORM_BARRIER_BIT;
131*61046927SAndroid Build Coastguard Worker
132*61046927SAndroid Build Coastguard Worker /* From section 7.11.2 of the OpenGL ES 3.1 specification:
133*61046927SAndroid Build Coastguard Worker *
134*61046927SAndroid Build Coastguard Worker * "When barriers is ALL_BARRIER_BITS, shader memory accesses will be
135*61046927SAndroid Build Coastguard Worker * synchronized relative to all these barrier bits, but not to other
136*61046927SAndroid Build Coastguard Worker * barrier bits specific to MemoryBarrier."
137*61046927SAndroid Build Coastguard Worker *
138*61046927SAndroid Build Coastguard Worker * That is, if barriers is the special value GL_ALL_BARRIER_BITS, then all
139*61046927SAndroid Build Coastguard Worker * barriers allowed by glMemoryBarrierByRegion should be activated."
140*61046927SAndroid Build Coastguard Worker */
141*61046927SAndroid Build Coastguard Worker if (barriers == GL_ALL_BARRIER_BITS) {
142*61046927SAndroid Build Coastguard Worker memory_barrier(ctx, all_allowed_bits);
143*61046927SAndroid Build Coastguard Worker return;
144*61046927SAndroid Build Coastguard Worker }
145*61046927SAndroid Build Coastguard Worker
146*61046927SAndroid Build Coastguard Worker /* From section 7.11.2 of the OpenGL ES 3.1 specification:
147*61046927SAndroid Build Coastguard Worker *
148*61046927SAndroid Build Coastguard Worker * "An INVALID_VALUE error is generated if barriers is not the special
149*61046927SAndroid Build Coastguard Worker * value ALL_BARRIER_BITS, and has any bits set other than those
150*61046927SAndroid Build Coastguard Worker * described above."
151*61046927SAndroid Build Coastguard Worker */
152*61046927SAndroid Build Coastguard Worker if (!no_error && (barriers & ~all_allowed_bits) != 0) {
153*61046927SAndroid Build Coastguard Worker _mesa_error(ctx, GL_INVALID_VALUE,
154*61046927SAndroid Build Coastguard Worker "glMemoryBarrierByRegion(unsupported barrier bit");
155*61046927SAndroid Build Coastguard Worker }
156*61046927SAndroid Build Coastguard Worker
157*61046927SAndroid Build Coastguard Worker memory_barrier(ctx, barriers);
158*61046927SAndroid Build Coastguard Worker }
159*61046927SAndroid Build Coastguard Worker
160*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_MemoryBarrierByRegion_no_error(GLbitfield barriers)161*61046927SAndroid Build Coastguard Worker _mesa_MemoryBarrierByRegion_no_error(GLbitfield barriers)
162*61046927SAndroid Build Coastguard Worker {
163*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
164*61046927SAndroid Build Coastguard Worker memory_barrier_by_region(ctx, barriers, true);
165*61046927SAndroid Build Coastguard Worker }
166*61046927SAndroid Build Coastguard Worker
167*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_MemoryBarrierByRegion(GLbitfield barriers)168*61046927SAndroid Build Coastguard Worker _mesa_MemoryBarrierByRegion(GLbitfield barriers)
169*61046927SAndroid Build Coastguard Worker {
170*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
171*61046927SAndroid Build Coastguard Worker memory_barrier_by_region(ctx, barriers, false);
172*61046927SAndroid Build Coastguard Worker }
173*61046927SAndroid Build Coastguard Worker
174*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_BlendBarrier(void)175*61046927SAndroid Build Coastguard Worker _mesa_BlendBarrier(void)
176*61046927SAndroid Build Coastguard Worker {
177*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
178*61046927SAndroid Build Coastguard Worker
179*61046927SAndroid Build Coastguard Worker if (!ctx->Extensions.KHR_blend_equation_advanced) {
180*61046927SAndroid Build Coastguard Worker _mesa_error(ctx, GL_INVALID_OPERATION,
181*61046927SAndroid Build Coastguard Worker "glBlendBarrier(not supported)");
182*61046927SAndroid Build Coastguard Worker return;
183*61046927SAndroid Build Coastguard Worker }
184*61046927SAndroid Build Coastguard Worker
185*61046927SAndroid Build Coastguard Worker ctx->pipe->texture_barrier(ctx->pipe, PIPE_TEXTURE_BARRIER_FRAMEBUFFER);
186*61046927SAndroid Build Coastguard Worker }
187*61046927SAndroid Build Coastguard Worker
188*61046927SAndroid Build Coastguard Worker void GLAPIENTRY
_mesa_FramebufferFetchBarrierEXT(void)189*61046927SAndroid Build Coastguard Worker _mesa_FramebufferFetchBarrierEXT(void)
190*61046927SAndroid Build Coastguard Worker {
191*61046927SAndroid Build Coastguard Worker GET_CURRENT_CONTEXT(ctx);
192*61046927SAndroid Build Coastguard Worker
193*61046927SAndroid Build Coastguard Worker if (!ctx->Extensions.EXT_shader_framebuffer_fetch_non_coherent) {
194*61046927SAndroid Build Coastguard Worker _mesa_error(ctx, GL_INVALID_OPERATION,
195*61046927SAndroid Build Coastguard Worker "glFramebufferFetchBarrierEXT(not supported)");
196*61046927SAndroid Build Coastguard Worker return;
197*61046927SAndroid Build Coastguard Worker }
198*61046927SAndroid Build Coastguard Worker
199*61046927SAndroid Build Coastguard Worker ctx->pipe->texture_barrier(ctx->pipe, PIPE_TEXTURE_BARRIER_FRAMEBUFFER);
200*61046927SAndroid Build Coastguard Worker }
201