Widen color state support on ES.
Indexed draw buffer (color state) support on ES is not core until 3.2.
Previously, we were failing (asserting) if color state was changed for
a non-zero attachment. This CL compares the state, and only asserts if the
color state actually differs per-attachment.
It also implements a disable_indexed_draw_buffers toggle, which allows a
test to check for the functionality in a platform-independent manner.
BUG=dawn:580, dawn:582
Change-Id: I11c67b0dd72f73e7302c06cad24e8a268fb37a76
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/34981
Commit-Queue: Stephen White <senorblanco@chromium.org>
Reviewed-by: Corentin Wallez <cwallez@chromium.org>
diff --git a/src/dawn_native/opengl/RenderPipelineGL.cpp b/src/dawn_native/opengl/RenderPipelineGL.cpp
index edabc71..9a5da5c 100644
--- a/src/dawn_native/opengl/RenderPipelineGL.cpp
+++ b/src/dawn_native/opengl/RenderPipelineGL.cpp
@@ -106,44 +106,46 @@
ColorAttachmentIndex attachment,
const ColorStateDescriptor* descriptor) {
GLuint colorBuffer = static_cast<GLuint>(static_cast<uint8_t>(attachment));
- if (gl.IsAtLeastGL(3, 0) || gl.IsAtLeastGLES(3, 2)) {
- if (BlendEnabled(descriptor)) {
- gl.Enablei(GL_BLEND, colorBuffer);
- gl.BlendEquationSeparatei(colorBuffer,
- GLBlendMode(descriptor->colorBlend.operation),
- GLBlendMode(descriptor->alphaBlend.operation));
- gl.BlendFuncSeparatei(colorBuffer,
- GLBlendFactor(descriptor->colorBlend.srcFactor, false),
- GLBlendFactor(descriptor->colorBlend.dstFactor, false),
- GLBlendFactor(descriptor->alphaBlend.srcFactor, true),
- GLBlendFactor(descriptor->alphaBlend.dstFactor, true));
- } else {
- gl.Disablei(GL_BLEND, colorBuffer);
- }
- gl.ColorMaski(colorBuffer, descriptor->writeMask & wgpu::ColorWriteMask::Red,
- descriptor->writeMask & wgpu::ColorWriteMask::Green,
- descriptor->writeMask & wgpu::ColorWriteMask::Blue,
- descriptor->writeMask & wgpu::ColorWriteMask::Alpha);
+ if (BlendEnabled(descriptor)) {
+ gl.Enablei(GL_BLEND, colorBuffer);
+ gl.BlendEquationSeparatei(colorBuffer,
+ GLBlendMode(descriptor->colorBlend.operation),
+ GLBlendMode(descriptor->alphaBlend.operation));
+ gl.BlendFuncSeparatei(colorBuffer,
+ GLBlendFactor(descriptor->colorBlend.srcFactor, false),
+ GLBlendFactor(descriptor->colorBlend.dstFactor, false),
+ GLBlendFactor(descriptor->alphaBlend.srcFactor, true),
+ GLBlendFactor(descriptor->alphaBlend.dstFactor, true));
} else {
- // TODO(crbug.com/dawn/582): Add validation to prevent this as it is not supported
- // on GLES < 3.2.
- DAWN_ASSERT(colorBuffer == 0);
- if (BlendEnabled(descriptor)) {
- gl.Enable(GL_BLEND);
- gl.BlendEquationSeparate(GLBlendMode(descriptor->colorBlend.operation),
- GLBlendMode(descriptor->alphaBlend.operation));
- gl.BlendFuncSeparate(GLBlendFactor(descriptor->colorBlend.srcFactor, false),
- GLBlendFactor(descriptor->colorBlend.dstFactor, false),
- GLBlendFactor(descriptor->alphaBlend.srcFactor, true),
- GLBlendFactor(descriptor->alphaBlend.dstFactor, true));
- } else {
- gl.Disable(GL_BLEND);
- }
- gl.ColorMask(descriptor->writeMask & wgpu::ColorWriteMask::Red,
- descriptor->writeMask & wgpu::ColorWriteMask::Green,
- descriptor->writeMask & wgpu::ColorWriteMask::Blue,
- descriptor->writeMask & wgpu::ColorWriteMask::Alpha);
+ gl.Disablei(GL_BLEND, colorBuffer);
}
+ gl.ColorMaski(colorBuffer, descriptor->writeMask & wgpu::ColorWriteMask::Red,
+ descriptor->writeMask & wgpu::ColorWriteMask::Green,
+ descriptor->writeMask & wgpu::ColorWriteMask::Blue,
+ descriptor->writeMask & wgpu::ColorWriteMask::Alpha);
+ }
+
+ void ApplyColorState(const OpenGLFunctions& gl, const ColorStateDescriptor* descriptor) {
+ if (BlendEnabled(descriptor)) {
+ gl.Enable(GL_BLEND);
+ gl.BlendEquationSeparate(GLBlendMode(descriptor->colorBlend.operation),
+ GLBlendMode(descriptor->alphaBlend.operation));
+ gl.BlendFuncSeparate(GLBlendFactor(descriptor->colorBlend.srcFactor, false),
+ GLBlendFactor(descriptor->colorBlend.dstFactor, false),
+ GLBlendFactor(descriptor->alphaBlend.srcFactor, true),
+ GLBlendFactor(descriptor->alphaBlend.dstFactor, true));
+ } else {
+ gl.Disable(GL_BLEND);
+ }
+ gl.ColorMask(descriptor->writeMask & wgpu::ColorWriteMask::Red,
+ descriptor->writeMask & wgpu::ColorWriteMask::Green,
+ descriptor->writeMask & wgpu::ColorWriteMask::Blue,
+ descriptor->writeMask & wgpu::ColorWriteMask::Alpha);
+ }
+
+ bool Equal(const BlendDescriptor& lhs, const BlendDescriptor& rhs) {
+ return lhs.operation == rhs.operation && lhs.srcFactor == rhs.srcFactor &&
+ lhs.dstFactor == rhs.dstFactor;
}
GLuint OpenGLStencilOperation(wgpu::StencilOperation stencilOperation) {
@@ -298,8 +300,25 @@
gl.Disable(GL_POLYGON_OFFSET_FILL);
}
- for (ColorAttachmentIndex attachmentSlot : IterateBitSet(GetColorAttachmentsMask())) {
- ApplyColorState(gl, attachmentSlot, GetColorStateDescriptor(attachmentSlot));
+ if (!GetDevice()->IsToggleEnabled(Toggle::DisableIndexedDrawBuffers)) {
+ for (ColorAttachmentIndex attachmentSlot : IterateBitSet(GetColorAttachmentsMask())) {
+ ApplyColorState(gl, attachmentSlot, GetColorStateDescriptor(attachmentSlot));
+ }
+ } else {
+ const ColorStateDescriptor* prevDescriptor = nullptr;
+ for (ColorAttachmentIndex attachmentSlot : IterateBitSet(GetColorAttachmentsMask())) {
+ const ColorStateDescriptor* descriptor = GetColorStateDescriptor(attachmentSlot);
+ if (!prevDescriptor) {
+ ApplyColorState(gl, descriptor);
+ prevDescriptor = descriptor;
+ } else if (!Equal(descriptor->alphaBlend, prevDescriptor->alphaBlend) ||
+ !Equal(descriptor->colorBlend, prevDescriptor->colorBlend) ||
+ descriptor->writeMask != prevDescriptor->writeMask) {
+ // TODO(crbug.com/dawn/582): Add validation to prevent this as it is not
+ // supported on GLES < 3.2.
+ ASSERT(false);
+ }
+ }
}
}