Skip to content

Conversation

@timmaffett
Copy link
Contributor

@timmaffett timmaffett commented Sep 17, 2025

Fixes #169442
Accomodates #167404 and some of #166944

This PR adds a FragmentProgram.fromBytes() method to allow loading of fragment shaders from outside the original asset bundle. This greatly extends the capabilities of the current restrictions of only allowing fragment shaders to be bundled in the build time asset bundle. (allowing many new capabilities, including items like the protection of shader source code via encryption, downloads of new shaders without reinstallation of program, runtime shader editing, ad infinitum). The referenced issues only partially touch upon why this feature is desperately needed.

This PR goes hand in hand with #175470 which allows versioning of impellerc outputs and protection for the engine from attempting to load incompatible versions of any of the impellerc output flat buffers. PR #175470 should be considered a required component of this PR to protect the engine from unexpected input.

I will incorporate unit tests for these capabilities which exercise the fromBytes() method - I wanted to initiate the conversation for now. I personally feel that the bang for the buck from this PR is extraordinary.

Other issues that this PR resolves or at least provides capabilities for that allow work-arounds:
resolves - #169442 - Allow for shader loading at runtime
partial - #171284 - Add support for loading assets with non-package paths in dart:ui APIs
(for the FragmentProgram.fromAsset() limitations .fromBytes() can be used to load your assets from
any AssetBundle)

Pre-launch Checklist

  • I read the [Contributor Guide] and followed the process outlined there for submitting PRs.
  • I read the [Tree Hygiene] wiki page, which explains my responsibilities.
  • I read and followed the [Flutter Style Guide], including [Features we expect every widget to implement].
  • I signed the [CLA].
  • I listed at least one issue that this PR fixes in the description above.
  • I updated/added relevant documentation (doc comments with ///).
  • [FORTHCOMING] I added new tests to check the change I am making, or this PR is [test-exempt].
  • I followed the [breaking change policy] and added [Data Driven Fixes] where supported.
  • All existing and new tests are passing.

@flutter-dashboard
Copy link

It looks like this pull request may not have tests. Please make sure to add tests or get an explicit test exemption before merging.

If you are not sure if you need tests, consider this rule of thumb: the purpose of a test is to make sure someone doesn't accidentally revert the fix. Ask yourself, is there anything in your PR that you feel it is important we not accidentally revert back to how it was before your fix?

Reviewers: Read the Tree Hygiene page and make sure this patch meets those guidelines before LGTMing. If you believe this PR qualifies for a test exemption, contact "@test-exemption-reviewer" in the #hackers channel in Discord (don't just cc them here, they won't see it!). The test exemption team is a small volunteer group, so all reviewers should feel empowered to ask for tests, without delegating that responsibility entirely to the test exemption group.

@github-actions github-actions bot added engine flutter/engine related. See also e: labels. platform-web Web applications specifically labels Sep 17, 2025
Copy link
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces FragmentProgram.fromBytes, a valuable addition that allows loading fragment shaders from byte data, extending beyond the asset bundle. The implementation is consistent across the C++ and web engines, and the refactoring in the C++ code to share logic between fromAsset and fromBytes is a nice improvement. My main feedback is to add a warning to the documentation about the potential for crashes if an incompatible shader version is loaded, as you've noted that versioning is handled in a separate PR.

Comment on lines +5244 to +5249
/// Creates a fragment program from the provided byte data.
///
/// The byte data must be produced as the output of the `impellerc`
/// compiler. The constructed object should then be reused via the
/// [fragmentShader] method to create [Shader] objects that can be used by
/// [Paint.shader].
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Given that loading shaders from bytes can be risky without version checking (as you mentioned in the PR description regarding #175470), it would be beneficial to add a warning to the documentation for fromBytes. This will help prevent developers from accidentally crashing their applications by loading incompatible shader versions.

Here's a suggested addition to the doc comment:

  /// Creates a fragment program from the provided byte data.
  ///
  /// The byte data must be produced as the output of the `impellerc`
  /// compiler. The constructed object should then be reused via the
  /// [fragmentShader] method to create [Shader] objects that can be used by
  /// [Paint.shader].
  ///
  /// > [!WARNING]
  /// > The format of the byte data is tied to the version of the Flutter engine.
  /// > Attempting to load a shader compiled with a different version of `impellerc`
  /// > than the one used by the engine may result in a crash or unexpected behavior.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I stated that this PR goes hand in hand with #175470 and with such a requirement a doc comment would not be necessary because this PR should not be merged without #175470 being merged. I separated them as #175470 has other general advantages outside of protecting FragmentProgram (ie protecting ShaderLibrary, et al.)

@gaaclarke gaaclarke changed the title add FragmentProgram.fromBytes to c++ and web engines. Fixes #169442, Accomodates #167404 and some of #166944 add FragmentProgram.fromBytes to c++ and web engines. Oct 1, 2025
Copy link
Contributor

@harryterkelsen harryterkelsen left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM for the web bits. Don't have much familiarity with the native engine but the change looks pretty straightforward and correct to me there, too.

@mdebbar mdebbar added the triaged-web Triaged by Web platform team label Dec 3, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

engine flutter/engine related. See also e: labels. platform-web Web applications specifically triaged-web Triaged by Web platform team

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Allow for shader loading at runtime

3 participants