Repository navigation
Conversation
…ffer The default lengthInBytes of -1 reached the native side unchanged and became impeller::Range(offset, SIZE_MAX). On OpenGL ES that range is later uploaded with glBufferSubData, which fails with GL_INVALID_VALUE, so the flushed data never reached the GPU (and a debug engine aborted). The native entry point now maps a negative length to the rest of the buffer and rejects an offset outside the buffer (the same bound as the Dart checks) or a range past its end. It already returned a bool, but Dart declared the call as returning void and dropped it; Dart now reads the result and throws when the flush is refused, as overwrite does.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
DeviceBuffer.flush()defaultslengthInBytesto -1, documented as "the whole buffer", butInternalFlutterGpu_DeviceBuffer_Flushpassed it straight into animpeller::Rangeofsize_t, soflush()becameFlush(Range{0, SIZE_MAX}). On OpenGL ES,DeviceBufferGLESkeeps that as its dirty range and uploads it withglBufferSubData(..., SIZE_MAX, ...), which fails withGL_INVALID_VALUE: the data never reaches the GPU, and a debug engine aborts on the GL error check. Metal gets adidModifyRange:past the end of the buffer. Vulkan only worked becauseSIZE_MAXhappens to equalVK_WHOLE_SIZE.The native entry point now treats a negative length as "to the end of the buffer" and returns false for a range outside the buffer, with the same offset bound the Dart side checks. The Dart binding was declared as returning
Void, so that result was dropped; it isBoolnow, andflushthrows when the engine refuses, the wayoverwritedoes. -1 is normalized in one place, on the native side, so the entry point can't build an oversized range whoever calls it.device_buffer_unittests.ccis new and uses aMockDeviceBufferwithMOCK_METHOD(Flush)to check theRangethat reachesFlush.Where it was verified. macOS arm64,
host_debug_unopt_arm64, rebased on current main. Without the change three of the four C++ tests fail (Flush(Range{0, 0xFFFFFFFFFFFFFFFF})), and a newgpu_test.darttest that draws a triangle from a buffer flushed with defaults aborts underflutter_tester_opengleswithFatal GL Error GL_INVALID_VALUE(1281) encountered on call to glBufferSubData; Metal and Vulkan (SwiftShader) pass it. With the changegpu_unittests --gtest_filter='FlutterGpuDeviceBufferTest.*:FlutterGpuRenderPassTest.*:FlutterGpuRenderPipelineTest.*:FlutterGpuShaderLibraryTest.*'is 17/17 andgpu_test.dartpasses on all three backends.FlutterGpuCommandBufferTest.*is left out of the filter because it aborts in unopt builds on main as well (#194149).Fixes #194152
Pre-launch Checklist
///).