Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit

Permalink
[Impeller] OpenGLES: Ensure frag/vert textures are bound with unique …
Browse files Browse the repository at this point in the history
…texture units. (#47218)

The fragment shader texture bindings will smash into the texture units
used for the vertex shader bindings if the vertex and fragment shaders
both have textures.

Entities doesn't use any pipelines that tickle this case.
  • Loading branch information
bdero authored Nov 1, 2023
1 parent c562fd7 commit 787f9ef
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 15 deletions.
30 changes: 18 additions & 12 deletions impeller/renderer/backend/gles/buffer_bindings_gles.cc
Original file line number Diff line number Diff line change
Expand Up @@ -155,11 +155,15 @@ bool BufferBindingsGLES::BindUniformData(const ProcTableGLES& gl,
}
}

if (!BindTextures(gl, vertex_bindings, ShaderStage::kVertex)) {
std::optional<size_t> next_unit_index =
BindTextures(gl, vertex_bindings, ShaderStage::kVertex);
if (!next_unit_index.has_value()) {
return false;
}

if (!BindTextures(gl, fragment_bindings, ShaderStage::kFragment)) {
if (!BindTextures(gl, fragment_bindings, ShaderStage::kFragment,
*next_unit_index)
.has_value()) {
return false;
}

Expand Down Expand Up @@ -334,20 +338,22 @@ bool BufferBindingsGLES::BindUniformBuffer(const ProcTableGLES& gl,
return true;
}

bool BufferBindingsGLES::BindTextures(const ProcTableGLES& gl,
const Bindings& bindings,
ShaderStage stage) {
size_t active_index = 0;
std::optional<size_t> BufferBindingsGLES::BindTextures(
const ProcTableGLES& gl,
const Bindings& bindings,
ShaderStage stage,
size_t unit_start_index) {
size_t active_index = unit_start_index;
for (const auto& data : bindings.sampled_images) {
const auto& texture_gles = TextureGLES::Cast(*data.second.texture.resource);
if (data.second.texture.GetMetadata() == nullptr) {
VALIDATION_LOG << "No metadata found for texture binding.";
return false;
return std::nullopt;
}

auto location = ComputeTextureLocation(data.second.texture.GetMetadata());
if (location == -1) {
return false;
return std::nullopt;
}

//--------------------------------------------------------------------------
Expand All @@ -356,15 +362,15 @@ bool BufferBindingsGLES::BindTextures(const ProcTableGLES& gl,
if (active_index >= gl.GetCapabilities()->GetMaxTextureUnits(stage)) {
VALIDATION_LOG << "Texture units specified exceed the capabilities for "
"this shader stage.";
return false;
return std::nullopt;
}
gl.ActiveTexture(GL_TEXTURE0 + active_index);

//--------------------------------------------------------------------------
/// Bind the texture.
///
if (!texture_gles.Bind()) {
return false;
return std::nullopt;
}

//--------------------------------------------------------------------------
Expand All @@ -373,7 +379,7 @@ bool BufferBindingsGLES::BindTextures(const ProcTableGLES& gl,
///
const auto& sampler_gles = SamplerGLES::Cast(*data.second.sampler.resource);
if (!sampler_gles.ConfigureBoundTexture(texture_gles, gl)) {
return false;
return std::nullopt;
}

//--------------------------------------------------------------------------
Expand All @@ -386,7 +392,7 @@ bool BufferBindingsGLES::BindTextures(const ProcTableGLES& gl,
///
active_index++;
}
return true;
return active_index;
}

} // namespace impeller
7 changes: 4 additions & 3 deletions impeller/renderer/backend/gles/buffer_bindings_gles.h
Original file line number Diff line number Diff line change
Expand Up @@ -70,9 +70,10 @@ class BufferBindingsGLES {
Allocator& transients_allocator,
const BufferResource& buffer);

bool BindTextures(const ProcTableGLES& gl,
const Bindings& bindings,
ShaderStage stage);
std::optional<size_t> BindTextures(const ProcTableGLES& gl,
const Bindings& bindings,
ShaderStage stage,
size_t unit_start_index = 0);

BufferBindingsGLES(const BufferBindingsGLES&) = delete;

Expand Down

0 comments on commit 787f9ef

Please sign in to comment.