Commit Graph
20 Commits
Author SHA1 Message Date
swung0x48 8c5c39b3c3 [Feat, Test] (MG_Impl): glBindTextures and glBindImageTextures were no-op stubs while GL_ARB_multi_bind was advertised 2026-08-12 02:38:03 -04:00
swung0x48 16c010985f [Fix, Test] (MG_Impl): multi-bind name rejection is per element, and only transform feedback constrains the range size to a multiple of four 2026-08-11 09:17:51 -04:00
swung0x48 7b593e39ef [Fix, Test] (MG_Impl, MG_State): negative-path GL errors for multi_bind, indirect_parameters, texture_storage, compute dispatch/link and buffer-range alignment; indexed getters answer the full pname table 2026-08-11 09:02:22 -04:00
BZLZHH 33ff177bb2 [Fix, Test] (MG_Impl, MG_State): advertised-extension conformance wave 1 - uniforms, validators, getters
First wave of the advertised-extension CTS campaign (targeted caselist: the
glcts groups of every extension both backends advertise, 4867 cases across the
KHR-GL41..46 namespaces). All frontend, shared by both backends:

- Non-square float matrix uniforms actually upload: glUniformMatrix{2x3,3x2,
  2x4,4x2,3x4,4x3}fv and the six glProgramUniformMatrix* twins were
  validate-only no-ops; they now write column-at-a-time at the global UBO's
  16-byte std140 column stride, honouring transpose. glUniformMatrix2fv had
  the sibling bug - mat2 written as 4 contiguous floats put column 1 at byte
  8 instead of 16. The readback path only ever un-padded mat3, so
  glGetUniformfv is fixed for mat2, mat3x2 (previously mis-gathered) and
  every non-square shape, with the bounds check widened to the padded span.
- glBindBufferRange validates offset/size at last: size <= 0, offset < 0,
  SSBO and UBO offset alignment, transform-feedback offset AND size
  multiples of 4 - all before any state write (a negative offset used to
  reach Range1D unchecked). glBindBuffersRange inherits per element, with
  the ARB_multi_bind up-front [first, first+count) checks added to the
  BindBuffersBase/Range and BindSamplers prologues.
- BufferSubData's second, wrong mapped-overlap test deleted (it rejected
  every write at or after a mapped range's start, mapped or not); the state
  layer's assert relaxed to the same half-open intersection the frontend
  checks. BufferStorage error precedence fixed: no-bound-buffer now beats
  bad-size/flags.
- glSamplerParameteri accepts the full GL_NEVER..GL_ALWAYS compare-func
  range (NEVER/LESS/EQUAL were rejected by a wrong lower bound).
  glBindSampler's unit gate uses GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS instead
  of the frontend array capacity, shared with glBindSamplers by construction.
- Getters: GL_MAX_SHADER_STORAGE_BLOCK_SIZE in glGetIntegerv; atomic-counter
  buffer limits; all 11 per-unit GL_TEXTURE_BINDING_* plus GL_SAMPLER_BINDING
  in glGetIntegeri_v; GL_VERTEX_ATTRIB_BINDING/_RELATIVE_OFFSET across the
  vertex-attrib query family; glGetFloati_v/glGetDoublei_v implemented (were
  stubs); KHR_debug limits raised to spec floors.
- glCreateShader records INVALID_ENUM for an unknown type (it previously
  handed out a usable name with no error at all); glCreateShaderProgramv
  validates count up front. glDispatchCompute/Indirect validate work-group
  counts, offset alignment and indirect-buffer presence.
- glVertexAttribIFormat & friends take a positive integer-type whitelist -
  GL_FLOAT/GL_HALF_FLOAT/GL_DOUBLE/GL_FIXED no longer slip through as
  integer attributes.

Gate (headless Mesa, default config = async on): 570/570 unit at default and
with the kill switch; ext caselist Espryt 76.29% -> 77.87% (+81 fixed, 6
crashes -> 0, the whole list now runs in one glcts process), Magma 75.94% ->
77.58% (+80 fixed, 0 newly broken); KHR-GL33 full mustpass lost nothing
(9884/9886, the 2 known Mesa-drift failures); retrace smoke clean (the
bsl-GLES miss is the documented golden drift, bit-identical on the pristine
baseline). The 4 DirectGLES direct_state_access.renderbuffers_storage* cases
that turned red are a PRE-EXISTING GL_FRAMEBUFFER_SRGB cross-test leak,
A/B-proven on an unpatched 2e6fc1ff build - wave 1 removed the two accidental
maskers (a crash partition and a failing case whose error path reset the
state). Fixing the leak itself is queued.
2026-08-09 04:39:22 -04:00
BZLZHH dd60ff39ce [Feat] (MG_State, MG_Impl, MG_Backend, MG_Util): make the border colour real sampler state
glGetSamplerParameterfv(sampler, GL_TEXTURE_BORDER_COLOR) raised INVALID_ENUM,
because MobileGL kept the border colour on the texture object and
GetSamplerParam_State had no case for it at all. That is the first thing
direct_state_access.samplers_defaults asks, so the case threw before reaching
any of the defaults it was written to check.

GL 4.6 core table 23.18 lists TEXTURE_BORDER_COLOR as sampler state, so it moves
to SamplerParameters and TextureObjectBase reaches it through the SamplerObject
it already owns - one source of truth, and a sampler object bound over a texture
now supplies its own border colour, which is what GL says should happen. The
texture params version still moves on a write, because the DirectGLES texture
sync memoises on it. glSamplerParameter{fv,Iiv,Iuiv} and their getters read and
write all four components in whichever representation the caller used, and the
three representations are kept in step so any getter has an answer. The bogus
[0,1] and [0,255] range checks are gone: GL clamps a border colour when a
fixed-point format is sampled, it does not reject it.

DirectVulkan's ResolveVkBorderColor now reads the sampler rather than the
texture. DirectGLES gained a glSamplerParameterfv in its sampler sync, and both
that and the pre-existing glTexParameterfv are gated on a new
SupportsTextureBorderClamp capability - ES 3.2 core, or EXT/OES_texture_border_clamp
before it - since without the extension every such call is INVALID_ENUM on the
driver. DriverPost gains the matching row per the POST rule, saying what a user
actually loses when it is missing.

Takes direct_state_access.samplers_defaults from failing to passing on both
backends.
2026-08-05 04:45:55 -04:00
BZLZHH 8eaf2d0069 [Fix] (MG_Impl): create sampler objects at Gen; guard combined-format CopyTexImage
glGenSamplers creates the sampler objects themselves (unlike texture and
buffer names), so glIsSampler must answer GL_TRUE before any bind - the
names now get their state vectors at Gen time (KHR-GL33.api.coverage).

glCopyTexImage2D with a combined DEPTH_STENCIL internalformat now
requires both halves in the read framebuffer and reports
GL_INVALID_OPERATION when only the depth or only the stencil attachment
point is populated (packed_depth_stencil.validate_errors.*).
2026-08-01 00:27:05 -04:00
swung0x48 a08669df72 [Fix] (MG_Impl/GLImpl): stop recording GL errors on the delete/query paths of every object family - glDeleteBuffers/VertexArrays/Renderbuffers/Framebuffers must silently ignore unknown names and glIsTexture must never raise, while glBindSampler now reports INVALID_OPERATION like the other bind entry points 2026-07-16 22:11:43 -04:00
swung0x48 5d6b544021 [Fix] (MG_Impl/Texture): support anisotropic sampler parameters 2026-07-16 21:39:38 -04:00
swung0x48andClaude Fable 5 a6a5edf573 [Perf] (MG_Backend/DirectGLES, MG_Impl): cache link-time lookups, bound unit scans, honor eglSwapInterval
- BackendProgramObjectImpl::CacheResourceLocations resolves every
  glGetUniformBlockIndex / glGetUniformLocation string query once per
  link and establishes the block binding points there. Per draw,
  BindCurrentProgramWithResources now uses the cached indices, re-issues
  glUniform1i only when a sampler's unit actually changed (program state
  persists), uploads the global UBO only when its content version moved,
  and skips redundant glUseProgram binds (guard reset on program-name
  reuse, MakeCurrent, and every explicit glUseProgram(0)). The caches are
  invalidated through ProgramObject's link version, which also makes a
  relinked program finally re-sync its backend program.
- Track a texture-unit high-water mark (fed by glBindTexture /
  glBindTextureUnit / glBindSampler / glBindImageTexture) so the two
  per-draw unit scans (MAX_TEXTURE_IMAGE_UNITS is 192) and the
  texture-deletion unbind loop only walk units that were ever touched.
- Forward the app's eglSwapInterval to the native EGL surface through a
  new BackendObject::SetEGLSwapInterval hook (applied immediately when
  the surface exists, otherwise deferred to surface creation /
  MakeCurrent). "VSync off" finally reaches the hardware - DirectGLES
  was hard-locked to the display refresh before.

The driver-side cost of the per-draw string lookups was about half of a
30% Adreno driver hotspot; libMobileGL's share of the vanilla render
thread fell from 22% to 9% (simpleperf, Adreno 830).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-09 12:12:51 +00:00
BZLZHH 727939af5b [Fix] (MG_Impl, MG_State, MG_Backend, MG_Util): Do source audit by Codex. 2026-06-09 15:34:19 +08:00
swung0x48 8e4a4359b4 [Chore] (MG_Backend/DirectVulkan): eliminate vague texture binding fallbacks 2026-05-05 18:34:44 +08:00
BZLZHH 15e24cda78 [Perf|Improvement] (All): Improve performance & optimize code. 2026-02-23 16:00:38 +08:00
BZLZHH 20fbfc2956 [Chore] (LICENSE): Switch project license to LGPLv3. 2026-01-18 09:33:33 +08:00
BZLZHH 3714e275ab [Chore] (All): Update copyright year in source code files. 2026-01-01 00:42:06 +08:00
BZLZHH e7d9da42dc [Chore] (All): Adjust copyright declaration. 2025-12-31 21:49:54 +08:00
BZLZHH 8ed8efe347 [Chore] (All): Add standardized source file header and update script. 2025-12-31 15:45:34 +08:00
BZLZHH a6b34ee5bf [Chore] (...): Format code. 2025-11-28 15:17:50 +08:00
swung0x48 ff0a3c5b9a [Feat] (MG_Util/Converters, MG_State/Sampler, MG_State/Texture): properly implement min/mag/mip filters 2025-11-17 13:40:34 +08:00
BZLZHH 131c9a2db6 [Improvement] (MG_Impl/Sampler): Create sampler object even when not bound. 2025-11-16 02:19:16 +08:00
BZLZHH 60bb091927 [Feat] (MG_Impl/Sampler): Implement full sampler object frontend. 2025-11-16 00:36:21 +08:00