From 230a5d8a9347dde220a047aba802ed4ff556cf8a Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Fri, 31 Oct 2025 14:28:45 -0700 Subject: [PATCH] Fix GLES2 UBO emulation (#9392) The binding cache didn't take into account the UBO offset. FIXES=[456802974] --- filament/backend/src/opengl/GLDescriptorSet.cpp | 5 +---- filament/backend/src/opengl/OpenGLProgram.cpp | 9 +++++++-- filament/backend/src/opengl/OpenGLProgram.h | 3 ++- 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/filament/backend/src/opengl/GLDescriptorSet.cpp b/filament/backend/src/opengl/GLDescriptorSet.cpp index fc5f7b7e87..aacee30679 100644 --- a/filament/backend/src/opengl/GLDescriptorSet.cpp +++ b/filament/backend/src/opengl/GLDescriptorSet.cpp @@ -303,13 +303,10 @@ void GLDescriptorSet::bind( offset += offsets[dynamicOffsetIndex++]; } if (arg.bo) { - auto buffer = static_cast(arg.bo->gl.buffer) + offset; - p.updateUniforms(bindingPoint, arg.bo->gl.id, buffer, arg.bo->age); + p.updateUniforms(bindingPoint, arg.bo->gl.id, arg.bo->gl.buffer, arg.bo->age, offset); } } else if constexpr (std::is_same_v) { GLuint const unit = p.getTextureUnit(set, binding); - - if (arg.handle) { GLTexture const* const t = handleAllocator.handle_cast(arg.handle); gl.bindTexture(unit, t->gl.target, t->gl.id, t->gl.external); diff --git a/filament/backend/src/opengl/OpenGLProgram.cpp b/filament/backend/src/opengl/OpenGLProgram.cpp index 8975d001f6..74e433dc99 100644 --- a/filament/backend/src/opengl/OpenGLProgram.cpp +++ b/filament/backend/src/opengl/OpenGLProgram.cpp @@ -262,20 +262,25 @@ void OpenGLProgram::initializeProgramState(OpenGLContext& context, GLuint progra } void OpenGLProgram::updateUniforms( - uint32_t index, GLuint id, void const* buffer, uint16_t age) const noexcept { + uint32_t const index, GLuint const id, void const* buffer, + uint16_t const age, uint32_t const offset) const noexcept { assert_invariant(mUniformsRecords); assert_invariant(buffer); // only update the uniforms if the UBO has changed since last time we updated UniformsRecord const& records = mUniformsRecords[index]; - if (records.id == id && records.age == age) { + if (records.id == id && records.age == age && records.offset == offset) { return; } records.id = id; records.age = age; + records.offset = offset; assert_invariant(records.uniforms.size() == records.locations.size()); + // apply the offset to the buffer + buffer = static_cast(buffer) + offset; + for (size_t i = 0, c = records.uniforms.size(); i < c; i++) { Program::Uniform const& u = records.uniforms[i]; GLint const loc = records.locations[i]; diff --git a/filament/backend/src/opengl/OpenGLProgram.h b/filament/backend/src/opengl/OpenGLProgram.h index 4d4a1ca17b..c5ceccfbc0 100644 --- a/filament/backend/src/opengl/OpenGLProgram.h +++ b/filament/backend/src/opengl/OpenGLProgram.h @@ -88,7 +88,7 @@ public: } // For ES2 only - void updateUniforms(uint32_t index, GLuint id, void const* buffer, uint16_t age) const noexcept; + void updateUniforms(uint32_t index, GLuint id, void const* buffer, uint16_t age, uint32_t offset) const noexcept; void setRec709ColorSpace(bool rec709) const noexcept; PushConstantBundle getPushConstants() { @@ -123,6 +123,7 @@ private: LocationInfo locations; mutable GLuint id = 0; mutable uint16_t age = std::numeric_limits::max(); + mutable uint32_t offset = 0; }; UniformsRecord const* mUniformsRecords = nullptr; GLint mRec709Location : 24; // 4 bytes