From 534ec65ddafbacba2d38fdb11e6ed809e1e5d6f7 Mon Sep 17 00:00:00 2001 From: BZLZHH Date: Wed, 5 Aug 2026 02:26:50 +0000 Subject: [PATCH] [Fix] (MG_Util): ask the ES driver for the texture buffer offset alignment The DirectGLES capability probe queried GL_TEXTURE_BUFFER_OFFSET_ALIGNMENT with a bare glGetIntegerv while every other query in the same function goes through glesFuncs. A bare call resolves to MobileGL's own exported entry point, which answers that pname out of the capability table this code is in the middle of filling in, so the value read back was the default it started from and the driver's real alignment never arrived. The backend therefore advertised an alignment of 1. An application that trusts that - which is the only thing it can do - passes glTextureBufferRange an offset the ES driver cannot honour, and the driver produces a texture that reads as zeros with no error anywhere. The alignment llvmpipe actually wants is 16. Takes direct_state_access.textures_buffer_* from 3 to 30 of 30 on DirectGLES, and the whole DSA group from 66.85% to 74.12%. DirectVulkan was unaffected: its alignment comes from a Vulkan device limit and was already right. --- MobileGL/MG_Util/BackendLoaders/OpenGL/Loader.cpp | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/MobileGL/MG_Util/BackendLoaders/OpenGL/Loader.cpp b/MobileGL/MG_Util/BackendLoaders/OpenGL/Loader.cpp index 41a85fc0..17e33004 100644 --- a/MobileGL/MG_Util/BackendLoaders/OpenGL/Loader.cpp +++ b/MobileGL/MG_Util/BackendLoaders/OpenGL/Loader.cpp @@ -1056,9 +1056,17 @@ namespace MobileGL::MG_Util::BackendLoader { caps.MaxComputeWorkGroupInvocations = maxComputeWorkGroupInvocations; caps.MaxShaderStorageBufferBindings = maxShaderStorageBufferBindings; caps.MaxTextureBufferSize = maxTextureBufferSize; + // Through glesFuncs, like every other capability query here: a bare glGetIntegerv resolves + // to MobileGL's own exported entry point, which answers this pname from the very + // capability table being filled in - so the driver's real alignment never arrived and the + // backend reported an unconstrained offset it cannot honour. GLint textureBufferOffsetAlignment = 1; - glGetIntegerv(GL_TEXTURE_BUFFER_OFFSET_ALIGNMENT, &textureBufferOffsetAlignment); - while (glGetError() != GL_NO_ERROR) {} + glesFuncs.glGetIntegerv(GL_TEXTURE_BUFFER_OFFSET_ALIGNMENT, &textureBufferOffsetAlignment); + // Core in ES 3.2 and in EXT_texture_buffer; an older context rejects the pname and leaves + // the default in place. + if (glesFuncs.glGetError) { + while (glesFuncs.glGetError() != GL_NO_ERROR) {} + } caps.TextureBufferOffsetAlignment = std::max(1, textureBufferOffsetAlignment); caps.MaxUniformBufferBindings = maxUniformBufferBindings; caps.MaxUniformBlockSize = maxUniformBlockSize;