Blender V5.0
gl_state.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2020 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
8
9#include "BKE_global.hh"
10
11#include "BLI_math_base.h"
12#include "BLI_math_bits.h"
13
14#include "GPU_capabilities.hh"
15
16#include "gl_context.hh"
17#include "gl_framebuffer.hh"
18#include "gl_texture.hh"
19
20#include "gl_state.hh"
21
22namespace blender::gpu {
23
24/* -------------------------------------------------------------------- */
27
29{
30 /* Set other states that never change. */
31 glEnable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
32 glEnable(GL_MULTISAMPLE);
33
34 glDisable(GL_DITHER);
35
36 glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
37 glPixelStorei(GL_PACK_ALIGNMENT, 1);
38 glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
39
40 /* Takes precedence over #GL_PRIMITIVE_RESTART.
41 * Sets restart index correctly following the IBO type. */
42 glEnable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
43
44 /* Limits. */
45 glGetFloatv(GL_ALIASED_LINE_WIDTH_RANGE, line_width_range_);
46
47 /* Force update using default state. */
48 current_ = ~state;
49 current_mutable_ = ~mutable_state;
50 set_state(state);
51 set_mutable_state(mutable_state);
52}
53
55{
56 this->set_state(this->state);
57 this->set_mutable_state(this->mutable_state);
58 this->texture_bind_apply();
59 this->image_bind_apply();
60
61 /* This is needed by gpu_py_offscreen. */
62 active_fb->apply_state();
63};
64
66{
67 /* Little exception for clip distances since they need to keep the old count correct. */
68 uint32_t clip_distances = current_.clip_distances;
69 current_ = ~this->state;
70 current_.clip_distances = clip_distances;
71 current_mutable_ = ~this->mutable_state;
72 this->set_state(this->state);
73 this->set_mutable_state(this->mutable_state);
74};
75
76void GLStateManager::set_state(const GPUState &state)
77{
78 GPUState changed = state ^ current_;
79
80 if (changed.blend != 0) {
81 set_blend((GPUBlend)state.blend);
82 }
83 if (changed.write_mask != 0) {
84 set_write_mask((GPUWriteMask)state.write_mask);
85 }
86 if (changed.depth_test != 0) {
87 set_depth_test((GPUDepthTest)state.depth_test);
88 }
89 if (changed.stencil_test != 0 || changed.stencil_op != 0) {
90 set_stencil_test((GPUStencilTest)state.stencil_test, (GPUStencilOp)state.stencil_op);
91 set_stencil_mask((GPUStencilTest)state.stencil_test, mutable_state);
92 }
93 if (changed.clip_distances != 0) {
94 set_clip_distances(state.clip_distances, current_.clip_distances);
95 }
96 if (changed.culling_test != 0) {
97 set_backface_culling((GPUFaceCullTest)state.culling_test);
98 }
99 if (changed.logic_op_xor != 0) {
100 set_logic_op(state.logic_op_xor);
101 }
102 if (changed.invert_facing != 0) {
103 set_facing(state.invert_facing);
104 }
105 if (changed.provoking_vert != 0) {
106 set_provoking_vert((GPUProvokingVertex)state.provoking_vert);
107 }
108 if (changed.shadow_bias != 0) {
109 set_shadow_bias(state.shadow_bias);
110 }
111 if (changed.clip_control != 0) {
112 set_clip_control(state.clip_control);
113 }
114
115 /* TODO: remove. */
116 if (changed.polygon_smooth) {
117 if (state.polygon_smooth) {
118 glEnable(GL_POLYGON_SMOOTH);
119 }
120 else {
121 glDisable(GL_POLYGON_SMOOTH);
122 }
123 }
124 if (changed.line_smooth) {
125 if (state.line_smooth) {
126 glEnable(GL_LINE_SMOOTH);
127 }
128 else {
129 glDisable(GL_LINE_SMOOTH);
130 }
131 }
132
133 current_ = state;
134}
135
136void GLStateManager::set_mutable_state(const GPUStateMutable &state)
137{
138 GPUStateMutable changed = state ^ current_mutable_;
139
140 /* TODO: remove, should be uniform. */
141 if (float_as_uint(changed.point_size) != 0) {
142 if (state.point_size > 0.0f) {
143 glEnable(GL_PROGRAM_POINT_SIZE);
144 }
145 else {
146 glDisable(GL_PROGRAM_POINT_SIZE);
147 glPointSize(fabsf(state.point_size));
148 }
149 }
150
151 if (float_as_uint(changed.line_width) != 0) {
152 /* TODO: remove, should use wide line shader. */
153 glLineWidth(clamp_f(state.line_width, line_width_range_[0], line_width_range_[1]));
154 }
155
156 if (float_as_uint(changed.depth_range[0]) != 0 || float_as_uint(changed.depth_range[1]) != 0) {
157 /* TODO: remove, should modify the projection matrix instead. */
158 glDepthRange(UNPACK2(state.depth_range));
159 }
160
161 if (changed.stencil_compare_mask != 0 || changed.stencil_reference != 0 ||
162 changed.stencil_write_mask != 0)
163 {
164 set_stencil_mask((GPUStencilTest)current_.stencil_test, state);
165 }
166
167 current_mutable_ = state;
168}
169
171
172/* -------------------------------------------------------------------- */
175
176void GLStateManager::set_write_mask(const GPUWriteMask value)
177{
178 glDepthMask((value & GPU_WRITE_DEPTH) != 0);
179 glColorMask((value & GPU_WRITE_RED) != 0,
180 (value & GPU_WRITE_GREEN) != 0,
181 (value & GPU_WRITE_BLUE) != 0,
182 (value & GPU_WRITE_ALPHA) != 0);
183
184 if (value == GPU_WRITE_NONE) {
185 glEnable(GL_RASTERIZER_DISCARD);
186 }
187 else {
188 glDisable(GL_RASTERIZER_DISCARD);
189 }
190}
191
192void GLStateManager::set_depth_test(const GPUDepthTest value)
193{
194 GLenum func;
195 switch (value) {
196 case GPU_DEPTH_LESS:
197 func = GL_LESS;
198 break;
200 func = GL_LEQUAL;
201 break;
202 case GPU_DEPTH_EQUAL:
203 func = GL_EQUAL;
204 break;
206 func = GL_GREATER;
207 break;
209 func = GL_GEQUAL;
210 break;
211 case GPU_DEPTH_ALWAYS:
212 default:
213 func = GL_ALWAYS;
214 break;
215 }
216
217 if (value != GPU_DEPTH_NONE) {
218 glEnable(GL_DEPTH_TEST);
219 glDepthFunc(func);
220 }
221 else {
222 glDisable(GL_DEPTH_TEST);
223 }
224}
225
226void GLStateManager::set_stencil_test(const GPUStencilTest test, const GPUStencilOp operation)
227{
228 switch (operation) {
230 glStencilOp(GL_KEEP, GL_KEEP, GL_REPLACE);
231 break;
233 glStencilOpSeparate(GL_BACK, GL_KEEP, GL_KEEP, GL_INCR_WRAP);
234 glStencilOpSeparate(GL_FRONT, GL_KEEP, GL_KEEP, GL_DECR_WRAP);
235 break;
237 glStencilOpSeparate(GL_BACK, GL_KEEP, GL_DECR_WRAP, GL_KEEP);
238 glStencilOpSeparate(GL_FRONT, GL_KEEP, GL_INCR_WRAP, GL_KEEP);
239 break;
241 default:
242 glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
243 }
244
245 if (test != GPU_STENCIL_NONE) {
246 glEnable(GL_STENCIL_TEST);
247 }
248 else {
249 glDisable(GL_STENCIL_TEST);
250 }
251}
252
253void GLStateManager::set_stencil_mask(const GPUStencilTest test, const GPUStateMutable &state)
254{
255 GLenum func;
256 switch (test) {
258 func = GL_NOTEQUAL;
259 break;
261 func = GL_EQUAL;
262 break;
264 func = GL_ALWAYS;
265 break;
266 case GPU_STENCIL_NONE:
267 default:
268 glStencilMask(0x00);
269 glStencilFunc(GL_ALWAYS, 0x00, 0x00);
270 return;
271 }
272
273 glStencilMask(state.stencil_write_mask);
274 glStencilFunc(func, state.stencil_reference, state.stencil_compare_mask);
275}
276
277void GLStateManager::set_clip_distances(const int new_dist_len, const int old_dist_len)
278{
279 for (int i = 0; i < new_dist_len; i++) {
280 glEnable(GL_CLIP_DISTANCE0 + i);
281 }
282 for (int i = new_dist_len; i < old_dist_len; i++) {
283 glDisable(GL_CLIP_DISTANCE0 + i);
284 }
285}
286
287void GLStateManager::set_logic_op(const bool enable)
288{
289 if (enable) {
290 glEnable(GL_COLOR_LOGIC_OP);
291 glLogicOp(GL_XOR);
292 }
293 else {
294 glDisable(GL_COLOR_LOGIC_OP);
295 }
296}
297
298void GLStateManager::set_facing(const bool invert)
299{
300 glFrontFace((invert) ? GL_CW : GL_CCW);
301}
302
303void GLStateManager::set_backface_culling(const GPUFaceCullTest test)
304{
305 if (test != GPU_CULL_NONE) {
306 glEnable(GL_CULL_FACE);
307 glCullFace((test == GPU_CULL_FRONT) ? GL_FRONT : GL_BACK);
308 }
309 else {
310 glDisable(GL_CULL_FACE);
311 }
312}
313
314void GLStateManager::set_provoking_vert(const GPUProvokingVertex vert)
315{
316 GLenum value = (vert == GPU_VERTEX_FIRST) ? GL_FIRST_VERTEX_CONVENTION :
317 GL_LAST_VERTEX_CONVENTION;
318 glProvokingVertex(value);
319}
320
321void GLStateManager::set_shadow_bias(const bool enable)
322{
323 if (enable) {
324 glEnable(GL_POLYGON_OFFSET_FILL);
325 glEnable(GL_POLYGON_OFFSET_LINE);
326 /* 2.0 Seems to be the lowest possible slope bias that works in every case. */
327 glPolygonOffset(2.0f, 1.0f);
328 }
329 else {
330 glDisable(GL_POLYGON_OFFSET_FILL);
331 glDisable(GL_POLYGON_OFFSET_LINE);
332 }
333}
334
335void GLStateManager::set_clip_control(const bool enable)
336{
337 if (enable) {
338 /* Match Vulkan and Metal by default. */
339 glClipControl(GL_LOWER_LEFT, GL_ZERO_TO_ONE);
340 }
341 else {
342 glClipControl(GL_LOWER_LEFT, GL_NEGATIVE_ONE_TO_ONE);
343 }
344}
345
346void GLStateManager::set_blend(const GPUBlend value)
347{
355 GLenum src_rgb, src_alpha, dst_rgb, dst_alpha;
356 switch (value) {
357 default:
358 case GPU_BLEND_ALPHA: {
359 src_rgb = GL_SRC_ALPHA;
360 dst_rgb = GL_ONE_MINUS_SRC_ALPHA;
361 src_alpha = GL_ONE;
362 dst_alpha = GL_ONE_MINUS_SRC_ALPHA;
363 break;
364 }
366 src_rgb = GL_ONE;
367 dst_rgb = GL_ONE_MINUS_SRC_ALPHA;
368 src_alpha = GL_ONE;
369 dst_alpha = GL_ONE_MINUS_SRC_ALPHA;
370 break;
371 }
372 case GPU_BLEND_ADDITIVE: {
373 /* Do not let alpha accumulate but pre-multiply the source RGB by it. */
374 src_rgb = GL_SRC_ALPHA;
375 dst_rgb = GL_ONE;
376 src_alpha = GL_ZERO;
377 dst_alpha = GL_ONE;
378 break;
379 }
382 /* Let alpha accumulate. */
383 src_rgb = GL_ONE;
384 dst_rgb = GL_ONE;
385 src_alpha = GL_ONE;
386 dst_alpha = GL_ONE;
387 break;
388 }
389 case GPU_BLEND_MULTIPLY: {
390 src_rgb = GL_DST_COLOR;
391 dst_rgb = GL_ZERO;
392 src_alpha = GL_DST_ALPHA;
393 dst_alpha = GL_ZERO;
394 break;
395 }
396 case GPU_BLEND_INVERT: {
397 src_rgb = GL_ONE_MINUS_DST_COLOR;
398 dst_rgb = GL_ZERO;
399 src_alpha = GL_ZERO;
400 dst_alpha = GL_ONE;
401 break;
402 }
403 case GPU_BLEND_OIT: {
404 src_rgb = GL_ONE;
405 dst_rgb = GL_ONE;
406 src_alpha = GL_ZERO;
407 dst_alpha = GL_ONE_MINUS_SRC_ALPHA;
408 break;
409 }
411 src_rgb = GL_ONE_MINUS_DST_ALPHA;
412 dst_rgb = GL_SRC_ALPHA;
413 src_alpha = GL_ZERO;
414 dst_alpha = GL_SRC_ALPHA;
415 break;
416 }
418 src_rgb = GL_ONE_MINUS_DST_ALPHA;
419 dst_rgb = GL_ONE;
420 src_alpha = GL_ONE_MINUS_DST_ALPHA;
421 dst_alpha = GL_ONE;
422 break;
423 }
424 case GPU_BLEND_CUSTOM: {
425 src_rgb = GL_ONE;
426 dst_rgb = GL_SRC1_COLOR;
427 src_alpha = GL_ONE;
428 dst_alpha = GL_SRC1_ALPHA;
429 break;
430 }
432 src_rgb = GL_ZERO;
433 dst_rgb = GL_ONE_MINUS_SRC_ALPHA;
434 src_alpha = GL_ZERO;
435 dst_alpha = GL_ONE_MINUS_SRC_ALPHA;
436 break;
437 }
438 }
439
440 if (value == GPU_BLEND_SUBTRACT) {
441 glBlendEquation(GL_FUNC_REVERSE_SUBTRACT);
442 }
443 else {
444 glBlendEquation(GL_FUNC_ADD);
445 }
446
447 /* Always set the blend function. This avoid a rendering error when blending is disabled but
448 * GPU_BLEND_CUSTOM was used just before and the frame-buffer is using more than 1 color target.
449 */
450 glBlendFuncSeparate(src_rgb, dst_rgb, src_alpha, dst_alpha);
451 if (value != GPU_BLEND_NONE) {
452 glEnable(GL_BLEND);
453 }
454 else {
455 glDisable(GL_BLEND);
456 }
457}
458
460
461/* -------------------------------------------------------------------- */
464
465void GLStateManager::texture_bind(Texture *tex_, GPUSamplerState sampler_state, int unit)
466{
468 GLTexture *tex = static_cast<GLTexture *>(tex_);
469 if (G.debug & G_DEBUG_GPU) {
470 tex->check_feedback_loop();
471 }
472 /* Eliminate redundant binds. */
473 if ((textures_[unit] == tex->tex_id_) &&
474 (samplers_[unit] == GLTexture::get_sampler(sampler_state)))
475 {
476 return;
477 }
478 targets_[unit] = tex->target_;
479 textures_[unit] = tex->tex_id_;
480 samplers_[unit] = GLTexture::get_sampler(sampler_state);
481 tex->is_bound_ = true;
482 dirty_texture_binds_ |= 1ULL << unit;
483}
484
486{
487 glActiveTexture(GL_TEXTURE0);
488 glBindTexture(tex->target_, tex->tex_id_);
489 /* Will reset the first texture that was originally bound to slot 0 back before drawing. */
490 dirty_texture_binds_ |= 1ULL;
491 /* NOTE: This might leave this texture attached to this target even after update.
492 * In practice it is not causing problems as we have incorrect binding detection
493 * at higher level. */
494}
495
497{
498 GLTexture *tex = static_cast<GLTexture *>(tex_);
499 if (!tex->is_bound_) {
500 return;
501 }
502
503 GLuint tex_id = tex->tex_id_;
504 for (int i = 0; i < ARRAY_SIZE(textures_); i++) {
505 if (textures_[i] == tex_id) {
506 textures_[i] = 0;
507 samplers_[i] = 0;
508 dirty_texture_binds_ |= 1ULL << i;
509 }
510 }
511 tex->is_bound_ = false;
512}
513
515{
516 for (int i = 0; i < ARRAY_SIZE(textures_); i++) {
517 if (textures_[i] != 0) {
518 textures_[i] = 0;
519 samplers_[i] = 0;
520 dirty_texture_binds_ |= 1ULL << i;
521 }
522 }
523 this->texture_bind_apply();
524}
525
526void GLStateManager::texture_bind_apply()
527{
528 if (dirty_texture_binds_ == 0) {
529 return;
530 }
531 uint64_t dirty_bind = dirty_texture_binds_;
532 dirty_texture_binds_ = 0;
533
534 int first = bitscan_forward_uint64(dirty_bind);
535 int last = 64 - bitscan_reverse_uint64(dirty_bind);
536 int count = last - first;
537
539 glBindTextures(first, count, textures_ + first);
540 glBindSamplers(first, count, samplers_ + first);
541 }
542 else {
543 for (int unit = first; unit < last; unit++) {
544 if ((dirty_bind >> unit) & 1UL) {
545 glActiveTexture(GL_TEXTURE0 + unit);
546 glBindTexture(targets_[unit], textures_[unit]);
547 glBindSampler(unit, samplers_[unit]);
548 }
549 }
550 }
551}
552
554{
555 texture_unpack_row_length_ = len;
556}
557
559{
560 return texture_unpack_row_length_;
561}
562
564{
565 uint64_t bound_slots = 0;
566 for (int i = 0; i < ARRAY_SIZE(textures_); i++) {
567 if (textures_[i] != 0) {
568 bound_slots |= 1ULL << i;
569 }
570 }
571 return bound_slots;
572}
573
575
576/* -------------------------------------------------------------------- */
579
581{
582 /* Minimum support is 8 image in the fragment shader. No image for other stages. */
583 BLI_assert(unit < 8);
584 GLTexture *tex = static_cast<GLTexture *>(tex_);
585 if (G.debug & G_DEBUG_GPU) {
586 tex->check_feedback_loop();
587 }
588 images_[unit] = tex->tex_id_;
589 formats_[unit] = to_gl_internal_format(tex->format_);
591 tex->is_bound_image_ = true;
592 dirty_image_binds_ |= 1ULL << unit;
593}
594
596{
597 GLTexture *tex = static_cast<GLTexture *>(tex_);
598 if (!tex->is_bound_image_) {
599 return;
600 }
601
602 GLuint tex_id = tex->tex_id_;
603 for (int i = 0; i < ARRAY_SIZE(images_); i++) {
604 if (images_[i] == tex_id) {
605 images_[i] = 0;
607 dirty_image_binds_ |= 1ULL << i;
608 }
609 }
610 tex->is_bound_image_ = false;
611}
612
614{
615 for (int i = 0; i < ARRAY_SIZE(images_); i++) {
616 if (images_[i] != 0) {
617 images_[i] = 0;
618 dirty_image_binds_ |= 1ULL << i;
619 }
620 }
622 this->image_bind_apply();
623}
624
625void GLStateManager::image_bind_apply()
626{
627 if (dirty_image_binds_ == 0) {
628 return;
629 }
630 uint32_t dirty_bind = dirty_image_binds_;
631 dirty_image_binds_ = 0;
632
633 int first = bitscan_forward_uint(dirty_bind);
634 int last = 32 - bitscan_reverse_uint(dirty_bind);
635 int count = last - first;
636
638 glBindImageTextures(first, count, images_ + first);
639 }
640 else {
641 for (int unit = first; unit < last; unit++) {
642 if ((dirty_bind >> unit) & 1UL) {
643 glBindImageTexture(unit, images_[unit], 0, GL_TRUE, 0, GL_READ_WRITE, formats_[unit]);
644 }
645 }
646 }
647}
648
650{
651 uint8_t bound_slots = 0;
652 for (int i = 0; i < ARRAY_SIZE(images_); i++) {
653 if (images_[i] != 0) {
654 bound_slots |= 1ULL << i;
655 }
656 }
657 return bound_slots;
658}
659
661
662/* -------------------------------------------------------------------- */
665
667{
668 glMemoryBarrier(to_gl(barrier_bits));
669}
670
672{
673 if (gl_sync_ != nullptr) {
674 glDeleteSync(gl_sync_);
675 gl_sync_ = nullptr;
676 }
677}
678
680{
681 /* If fence is already signaled, create a newly signaled fence primitive. */
682 if (gl_sync_) {
683 glDeleteSync(gl_sync_);
684 }
685
686 gl_sync_ = glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
687 signalled_ = true;
688}
689
691{
692 /* Do not wait if fence does not yet exist. */
693 if (gl_sync_ == nullptr) {
694 return;
695 }
696 glWaitSync(gl_sync_, 0, GL_TIMEOUT_IGNORED);
697 signalled_ = false;
698}
699
700
701} // namespace blender::gpu
@ G_DEBUG_GPU
#define BLI_assert(a)
Definition BLI_assert.h:46
MINLINE float clamp_f(float value, float min, float max)
MINLINE unsigned int bitscan_forward_uint(unsigned int a)
MINLINE unsigned int float_as_uint(float f)
MINLINE unsigned int bitscan_reverse_uint(unsigned int a)
MINLINE unsigned int bitscan_forward_uint64(unsigned long long a)
MINLINE unsigned int bitscan_reverse_uint64(unsigned long long a)
unsigned int uint
#define UNPACK2(a)
#define ARRAY_SIZE(arr)
int GPU_max_textures()
GPUBarrier
Definition GPU_state.hh:29
GPUDepthTest
Definition GPU_state.hh:110
@ GPU_DEPTH_GREATER
Definition GPU_state.hh:116
@ GPU_DEPTH_EQUAL
Definition GPU_state.hh:115
@ GPU_DEPTH_ALWAYS
Definition GPU_state.hh:112
@ GPU_DEPTH_GREATER_EQUAL
Definition GPU_state.hh:117
@ GPU_DEPTH_LESS
Definition GPU_state.hh:113
@ GPU_DEPTH_LESS_EQUAL
Definition GPU_state.hh:114
@ GPU_DEPTH_NONE
Definition GPU_state.hh:111
GPUBlend
Definition GPU_state.hh:84
@ GPU_BLEND_ADDITIVE_PREMULT
Definition GPU_state.hh:90
@ GPU_BLEND_INVERT
Definition GPU_state.hh:95
@ GPU_BLEND_OIT
Definition GPU_state.hh:98
@ GPU_BLEND_MULTIPLY
Definition GPU_state.hh:91
@ GPU_BLEND_NONE
Definition GPU_state.hh:85
@ GPU_BLEND_ALPHA
Definition GPU_state.hh:87
@ GPU_BLEND_CUSTOM
Definition GPU_state.hh:103
@ GPU_BLEND_ADDITIVE
Definition GPU_state.hh:89
@ GPU_BLEND_SUBTRACT
Definition GPU_state.hh:92
@ GPU_BLEND_ALPHA_UNDER_PREMUL
Definition GPU_state.hh:104
@ GPU_BLEND_BACKGROUND
Definition GPU_state.hh:100
@ GPU_BLEND_ALPHA_PREMULT
Definition GPU_state.hh:88
@ GPU_BLEND_OVERLAY_MASK_FROM_ALPHA
Definition GPU_state.hh:107
GPUProvokingVertex
Definition GPU_state.hh:141
@ GPU_VERTEX_FIRST
Definition GPU_state.hh:143
GPUStencilTest
Definition GPU_state.hh:120
@ GPU_STENCIL_EQUAL
Definition GPU_state.hh:123
@ GPU_STENCIL_NEQUAL
Definition GPU_state.hh:124
@ GPU_STENCIL_ALWAYS
Definition GPU_state.hh:122
@ GPU_STENCIL_NONE
Definition GPU_state.hh:121
GPUWriteMask
Definition GPU_state.hh:16
@ GPU_WRITE_RED
Definition GPU_state.hh:18
@ GPU_WRITE_NONE
Definition GPU_state.hh:17
@ GPU_WRITE_GREEN
Definition GPU_state.hh:19
@ GPU_WRITE_BLUE
Definition GPU_state.hh:20
@ GPU_WRITE_DEPTH
Definition GPU_state.hh:22
@ GPU_WRITE_ALPHA
Definition GPU_state.hh:21
GPUFaceCullTest
Definition GPU_state.hh:135
@ GPU_CULL_FRONT
Definition GPU_state.hh:137
@ GPU_CULL_NONE
Definition GPU_state.hh:136
GPUStencilOp
Definition GPU_state.hh:127
@ GPU_STENCIL_OP_COUNT_DEPTH_FAIL
Definition GPU_state.hh:132
@ GPU_STENCIL_OP_COUNT_DEPTH_PASS
Definition GPU_state.hh:131
@ GPU_STENCIL_OP_REPLACE
Definition GPU_state.hh:129
@ GPU_STENCIL_OP_NONE
Definition GPU_state.hh:128
unsigned long long int uint64_t
static bool multi_bind_support
Definition gl_context.hh:66
static bool multi_bind_image_support
Definition gl_context.hh:67
void signal() override
Definition gl_state.cc:679
void wait() override
Definition gl_state.cc:690
void texture_bind_temp(GLTexture *tex)
Definition gl_state.cc:485
GLFrameBuffer * active_fb
Definition gl_state.hh:32
uint texture_unpack_row_length_get() const
Definition gl_state.cc:558
void image_unbind(Texture *tex) override
Definition gl_state.cc:595
void image_bind(Texture *tex, int unit) override
Definition gl_state.cc:580
void apply_state() override
Definition gl_state.cc:54
void texture_unpack_row_length_set(uint len) override
Definition gl_state.cc:553
void texture_unbind_all() override
Definition gl_state.cc:514
void issue_barrier(GPUBarrier barrier_bits) override
Definition gl_state.cc:666
void force_state() override
Definition gl_state.cc:65
void texture_bind(Texture *tex, GPUSamplerState sampler, int unit) override
Definition gl_state.cc:465
void image_unbind_all() override
Definition gl_state.cc:613
void texture_unbind(Texture *tex) override
Definition gl_state.cc:496
static GLuint get_sampler(const GPUSamplerState &sampler_state)
std::array< TextureWriteFormat, GPU_MAX_IMAGE > image_formats
TextureFormat format_get() const
int count
CCL_NAMESPACE_BEGIN ccl_device float invert(const float color, const float factor)
Definition invert.h:11
static ulong state[N]
#define G(x, y, z)
GLenum to_gl_internal_format(TextureFormat format)
static GLenum to_gl(const GPUAttachmentType type)
#define fabsf
i
Definition text_draw.cc:230
uint len