Part of https://github.com/flutter/flutter/issues/144430
This is a reland of https://dart-review.googlesource.com/c/sdk/+/356481 with the addition of dependencies to prevent races on directory creation.
Previously, this code did backflips to accomplish two goals
1. Collect the paths of all files that would be copied from one place to another after applying regex filters so that they could be listed as the "inputs" to a GN action.
2. Arrange so that the python script doing the above would only be invoked once during GN to reduce the cost of calling out to python.
However, this is exactly the use-case for the "depfile" parameter to a GN action. Instead of running the script during GN to populate the "inputs" list, when we run the copy_tree.py script, we can instead ask it to generate a depfile to collect all the input files that were actually copied after applying the regex filter. Using that, we don't have to run the python script at all during GN.
TEST=it builds
Change-Id: I593e2500544a9fff5dd9852d0d3370f97aafc464
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356620
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Zach Anderson <zra@google.com>
As part of merging Flutter's flutter/buildroot and flutter/engine repos,
Flutter is migrating all third-party dependencies from //third_party to
//flutter/third_party.
This change allows consumers of the Dart SDK (notably Flutter), to
override the path of their third_party/perfetto directory by setting
perfetto_root_path in //build_overrides/build.gn. The Dart SDK does
not override perfetto's path, but does override other variables
(perfetto_build_with_embedder) in the equivalent overrides file secondary/build_overrides/build.gn.
TEST=None. Refactor only; no semantic changes.
Issue: https://github.com/flutter/flutter/issues/144204
Change-Id: Ie3835a5507a39bf2d68b1c86d42c626093358b17
Part of: https://github.com/flutter/flutter/issues/67373
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356622
Reviewed-by: Zach Anderson <zra@google.com>
Commit-Queue: Chris Bracken <cbracken@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
This fixes a TODO: TODO(brianwilkerson): Replace this method with methods similar to
// `_addMembersOfClass`.
Sorted declaration types.
Made name more obvious that they for with enclosing.
Updated comments to highlight this once more.
Change-Id: I323143671b97f7a74d9411180c91dcd78a51579f
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356540
Reviewed-by: Phil Quitslund <pquitslund@google.com>
Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
See the changes made to http_client_request_profile.dart in
https://github.com/dart-lang/http/pull/1154/files
TEST=The "using HttpClientRequestProfile.requestData.bodySink" and
"using HttpClientRequestProfile.responseData.bodySink" test cases in
package:http_profile
CoreLibraryReviewExempt: This CL does not include any API changes, only
implementation changes
Change-Id: Ia91ea2e7fb287271d8d7ec2b9f3bff3168d57d6e
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356560
Commit-Queue: Derek Xu <derekx@google.com>
Reviewed-by: Ben Konyi <bkonyi@google.com>
This reverts commit f60d32167f.
Reason for revert: build failures in post submit
Original change's description:
> [gn] Deprecate copy_trees()
>
> Part of https://github.com/flutter/flutter/issues/144430
>
> Previously, this code did backflips to accomplish two goals
> 1. Collect the paths of all files that would be copied from one place to another after applying regex filters so that they could be listed as the "inputs" to a GN action.
> 2. Arrange so that the python script doing the above would only be invoked once during GN to reduce the cost of calling out to python.
>
> However, this is exactly the use-case for the "depfile" parameter to a GN action. Instead of running the script during GN to populate the "inputs" list, when we run the copy_tree.py script, we can instead ask it to generate a depfile to collect all the input files that were actually copied after applying the regex filter. Using that, we don't have to run the python script at all during GN.
>
> TEST=it builds
>
> Change-Id: I41a251ce4659119cdc3997bb2d6fc7ee0831bb6d
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356481
> Reviewed-by: Siva Annamalai <asiva@google.com>
> Commit-Queue: Zach Anderson <zra@google.com>
> Reviewed-by: Alexander Aprelev <aam@google.com>
Change-Id: Ie4409ed93a3c990fbce375dba1f2d9a3c735ea3f
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356308
Auto-Submit: Zach Anderson <zra@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
Commit-Queue: Zach Anderson <zra@google.com>
This reverts commit 094202bb91.
Reason for revert: Break flutter, this change should happen after
flutter being migrated to the same gn-sdk.
Original change's description:
> [Fuchsia] Remove the legacy gn build rules for fuchsia
>
> The updated test-scripts contains https://crrev.com/c/5341620 which
> allows to generate fidl apis with an env var controlled location
> rather than a hard-coded one. So the existing fuchsia gn build rules
> in dart/sdk become obsolete and can be fully removed in favor of the
> one in //third_party/fuchsia/gn-sdk/.
>
> Meanwhile the gn-sdk has been updated with
> https://crrev.com/c/5325282 to use api-level version'ed idk but not
> the ones in arch/.
>
> Cq-Include-Trybots: luci.dart.try:vm-fuchsia-release-arm64-try,vm-fuchsia-release-x64-try
> Tested: ^^^^^
> Bug: 40935282
> Change-Id: I2ce958e6db1ff8221beef7b7ff953c32bb4525ba
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355283
> Reviewed-by: Ryan Macnak <rmacnak@google.com>
> Reviewed-by: Alexander Thomas <athom@google.com>
> Commit-Queue: Zijie He <zijiehe@google.com>
Bug: 40935282
Change-Id: I7c455d1d362210523671c97d99ef018ede1743f4
Cq-Include-Trybots: luci.dart.try:vm-fuchsia-release-arm64-try,vm-fuchsia-release-x64-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356307
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
Auto-Submit: Zijie He <zijiehe@google.com>
Reviewed-by: Derek Xu <derekx@google.com>
Commit-Queue: Zijie He <zijiehe@google.com>
Part of https://github.com/flutter/flutter/issues/144430
Previously, this code did backflips to accomplish two goals
1. Collect the paths of all files that would be copied from one place to another after applying regex filters so that they could be listed as the "inputs" to a GN action.
2. Arrange so that the python script doing the above would only be invoked once during GN to reduce the cost of calling out to python.
However, this is exactly the use-case for the "depfile" parameter to a GN action. Instead of running the script during GN to populate the "inputs" list, when we run the copy_tree.py script, we can instead ask it to generate a depfile to collect all the input files that were actually copied after applying the regex filter. Using that, we don't have to run the python script at all during GN.
TEST=it builds
Change-Id: I41a251ce4659119cdc3997bb2d6fc7ee0831bb6d
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356481
Reviewed-by: Siva Annamalai <asiva@google.com>
Commit-Queue: Zach Anderson <zra@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
Previously, we only had descriptions of changes on a SourceChange. In order to support annotated edits over LSP for "Fix All in Workspace" we need to be able to track descriptions on each change within a file so that if we're fixing multiple different lints with a single SourceFileEdit they can be annotated/grouped in the UI.
In order to avoid every fix providing a description, ChangeBuilder has a field that allows recording the current change description and all builders created from it will use that description when creating their changes. This allows the BulkFixProcessor to set the description on behalf of each fix producer ensuring they all get descriptions (which is done in a follow-up CL along with Fix All in Workspace functionality).
Change-Id: Ie1c508056898bd4000a5505cf59a1e6d35d28da0
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356160
Commit-Queue: Brian Wilkerson <brianwilkerson@google.com>
Reviewed-by: Samuel Rawlins <srawlins@google.com>
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
This enables some compiling and running with multiple modules
and simple import graphs.
Change-Id: I467c0dd0c4f5b41b19353ae5114bae20547b94f0
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355508
Reviewed-by: Sigmund Cherem <sigmund@google.com>
Commit-Queue: Nicholas Shahan <nshahan@google.com>
The flag allows for overriding the default (amd) with the ddc module
format when using `--runtime=chrome`.
This is intended to make it easier to test and debug changes to
the ddc module system.
Change-Id: I34767e2e80e9c80af5870bb7f51bf9ebaf438336
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355507
Reviewed-by: Mark Zhou <markzipan@google.com>
Reviewed-by: Sigmund Cherem <sigmund@google.com>
Commit-Queue: Nicholas Shahan <nshahan@google.com>
Speculative and non-speculative shift instructions have different
representations of RHS input, so canonicalization of multiplication
into a shift should account for that.
Also, mark BinaryUint32Op instruction as always non-speculative -
it never needs to speculate as it is inserted by range analysis
after it can prove that it is valid to perform Uint32 op.
This prevents insertion of a speculative shift instruction in AOT
when BinaryUint32Op multiplication is canonicalized.
Fixes https://github.com/dart-lang/sdk/issues/55003
TEST=vm/dart/regress_55003_test
Change-Id: Ib1805ce2dc0e6f514e6f3b4a09be08808e75048b
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355820
Reviewed-by: Slava Egorov <vegorov@google.com>
Commit-Queue: Alexander Markov <alexmarkov@google.com>
The e2e test is for "how DDC is used in the language tests", more
realistic setupts to follow.
R=jakemac@google.com, nshahan@google.com
Change-Id: Iece44740d2e4d91748a7deef59f4e18ad42ac853
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356241
Auto-Submit: Morgan :) <davidmorgan@google.com>
Commit-Queue: Morgan :) <davidmorgan@google.com>
Reviewed-by: Jake Macdonald <jakemac@google.com>
Reviewed-by: Nicholas Shahan <nshahan@google.com>
This adds fast paths that avoid copying bytes from the input to a
temporary array when the current chunk has enough bytes for thing being
parsed.
Also avoids allocating a temporary array when parsing a 64-bit float by
allocating a single 8-byte buffer and reusing it.
This reduces runtime of a `HeapSnapshotGraph.fromChunks` call parsing a
91M snapshot in a single chunk from 2 seconds to 1.8 seconds. The
benchmark code is compiled with `dart2js -O4`.
Change-Id: I39d9579bcf488b17ecd0d5c7a84f93748c733920
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/340182
Reviewed-by: Ben Konyi <bkonyi@google.com>
Commit-Queue: Ömer Ağacan <omersa@google.com>
This is especially effective for collection / iterators / ...
in our corelib code. It may also benefit more devirtualization
opportunities.
class Foo<T> extends Bar with A<T>, B<T> ... {}
This results in around
* -0.99% in flutter_gallery_app_so_size armv8 flutter-release-sizeopt
* -0.35% in flute complex in wasm-O4
TEST=pkg/vm/test/transformations/mixin_deduplication_test
Change-Id: I8a48b8dc46d94240b79000b2b16797b4044ba330
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356400
Reviewed-by: Slava Egorov <vegorov@google.com>
Commit-Queue: Martin Kustermann <kustermann@google.com>
Ideally we would write each source next to each test to make tests more
readable, but clustering all tests to use a common test file really
helps boost the runtime of the end2end tests now that we reuse the same
page between tests that share the same code.
This CL refactos the tests to mostly use one shared test file. Doing so
speeds up tests between 2x-4x depending on the test.
Change-Id: I9afd00c6a42226899969e3f605ac18e0d2b1a906
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356285
Reviewed-by: Mark Zhou <markzipan@google.com>
Commit-Queue: Sigmund Cherem <sigmund@google.com>
Since we changed how the test driver sets up breakpoints, we now we
have the ability to reuse a page for multiple tests.
Before, the test harness would follow this sequence:
* on each group of tests, it would call `_initSource`, which sets up
a boostraper and code to execute on the browser. This code was
reused by all tests in the group.
* on each test, it would indirectly call `_loadScript`, which
navigated to brand new page for each test. If there were multiple
tests in a group, this would load the boostraper and code once per
test.
This CL keeps the sequence of operations the same, except, that
`_loadScript` will reuse the existing page if it already loaded the
boostraper and DDC code needed by the next test.
This greatly reduces the total running time of some of the
expresison compiler shards. On my local machine one such test took
24s before both this and the parent CL, but now takes about 5s.
Change-Id: I7774df9e83142b42efc4ad523f589758a2a4660c
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356301
Reviewed-by: Nicholas Shahan <nshahan@google.com>
Reviewed-by: Mark Zhou <markzipan@google.com>
Instead of pausing the application while loading, this
changes the bootstrap logic to not invoke main immediately.
Later the test harness uses an expression evaluation to
trigger the start of the application when it is ready for
it.
This change will enable the ability to reuse the same page
and script across multiple tests, which will save a lot of
test execution time (see related child CL).
Change-Id: Ifa1050ac777aabb3e21b69953e85c6578b3e0cc0
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356281
Reviewed-by: Mark Zhou <markzipan@google.com>
Reviewed-by: Nicholas Shahan <nshahan@google.com>
Adding this token adds a small layer of security since the caller needs to have gathered the uri in some way rather than just stumbling on the DTD port.
Change-Id: I0665f4718d162daf94cb49fa1c6f4206c83d77cd
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355220
Reviewed-by: Kenzie Davisson <kenzieschmoll@google.com>
Commit-Queue: Dan Chevalier <danchevalier@google.com>
Reviewed-by: Ben Konyi <bkonyi@google.com>
These tests became flaky after 3786c5e5ee
landed as DDS initialization became faster, making it more likely that
an isolate used in the test was not yet runnable.
Partly fixes https://github.com/dart-lang/sdk/issues/55133
Change-Id: Ic919cfa6c8bf2b8274efecfa2a78bc056f7e181e
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356340
Commit-Queue: Ben Konyi <bkonyi@google.com>
Reviewed-by: Derek Xu <derekx@google.com>
Currently, serialized dump info metadata (output of emitter phase) contains all the impacts created during codegen in a Map<MemberEntity, WorldImpact>. These impacts are already serialized in the output of the codegen phase. This is bad for two reasons: 1) The serialized bytes are duplicated. 2) The impacts cannot be GCed right after the emitter uses them, the dump info registry maintains a reference to them.
To mitigate this I've updated the registry to only store impacts for entities where the impacts are generated during the emitter phase (today only parameter stubs). Rather than try to re-generate those impacts during the dump info phase, we serialize them with the dump info metadata. However, most impacts are generated during the codegen phase and for these we deserialize them from the codegen results at the beginning of the dump info phase.
Change-Id: I1302b4ab759bca3d492bc6b40194d7a7720ed6f8
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/354580
Commit-Queue: Nate Biggs <natebiggs@google.com>
Reviewed-by: Sigmund Cherem <sigmund@google.com>
This CL introduces a way to mark all instances of a class as deeply
immutable.
In order to statically verify that all instances of a deeply immutable
class are immutable, a deeply immutable classes must have the following
properties:
1. All instance fields must
1. have a deeply immutable type,
2. be final, and
3. be non-late.
2. The class must be `final` or `sealed`. This ensures no
non-deeply-immutable subtypes are added by external code.
3. All subtypes must be deeply immutable. This ensures 1.1 can be
trusted.
4. The super type must be deeply immutable (except for Object).
Note that instances of some classes in the VM are deeply immutable
while their class cannot be marked immutable.
* SendPort, Capability, RegExp, and StackTrace are not `final` and
can be implemented by external code.
* UnmodifiableTypedDataViews do not have a public type. (It was
recently deprecated.)
See runtime/docs/deeply_immutable.md for more details.
Use case:
This enables attaching a `Dart_FinalizableHandle` to a deeply immutable
object and the deeply immutable object with other isolates in the same
isolate group.
(Note that `NativeFinalizer`s live in an isolate, and not an isolate
group. So this should currently _not_ be used with `NativeFinalizer`s.
See https://github.com/dart-lang/sdk/issues/55062 for making a
`NativeFinalizer.shared(` that would live in an isolate group instead
of in an isolate.)
Implementation details:
Before this CL, the `ImmutableBit` in the object header was only ever
set to true for predefined class ids (and for const objects). After
this CL, the bit can also be set to true for non const instances of
user-defined classes. The object allocation and initialization code has
been changed to deal with this new case. The immutability of a class is
saved in the class state bits. On object allocation and initialization
the immutability bit is read from the class for non-predefined class
ids.
TEST=runtime/tests/vm/dart/isolates/fast_object_copy2_test.dart
TEST=runtime/vm/isolate_reload_test.cc
TEST=tests/lib/isolate/deeply_immutable_*
Bug: https://github.com/dart-lang/sdk/issues/55120
Bug: https://github.com/dart-lang/sdk/issues/54885
Change-Id: Ib97fe589cb4f81673cb928c93e3093838d82132d
Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-fuchsia-release-x64-try,vm-kernel-linux-debug-x64-try,vm-kernel-precomp-linux-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-ubsan-linux-release-x64-try
Cq-Include-Trybots: dart-internal/g3.dart-internal.try:g3-cbuild-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/354902
Commit-Queue: Daco Harkes <dacoharkes@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
The updated test-scripts contains https://crrev.com/c/5341620 which
allows to generate fidl apis with an env var controlled location
rather than a hard-coded one. So the existing fuchsia gn build rules
in dart/sdk become obsolete and can be fully removed in favor of the
one in //third_party/fuchsia/gn-sdk/.
Meanwhile the gn-sdk has been updated with
https://crrev.com/c/5325282 to use api-level version'ed idk but not
the ones in arch/.
Cq-Include-Trybots: luci.dart.try:vm-fuchsia-release-arm64-try,vm-fuchsia-release-x64-try
Tested: ^^^^^
Bug: 40935282
Change-Id: I2ce958e6db1ff8221beef7b7ff953c32bb4525ba
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355283
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Thomas <athom@google.com>
Commit-Queue: Zijie He <zijiehe@google.com>
Revisions updated by `dart tools/rev_sdk_deps.dart`.
dartdoc (cec45fb..0de8aff):
0de8aff3 2024-03-06 Sam Rawlins Generate docs for enum static methods. (dart-lang/dartdoc#3697)
9eafdc64 2024-03-06 Sam Rawlins Rewrite Library.allOriginalModelElementNames. (dart-lang/dartdoc#3698)
e8f36333 2024-03-06 Sam Rawlins Fix SDK GitHub action with some stub headers and footers (dart-lang/dartdoc#3704)
58c065d4 2024-03-05 Sam Rawlins Bump snippets activated to 0.4.3 (dart-lang/dartdoc#3702)
http (470d2c3..8d3c647):
8d3c647 2024-03-06 Brian Quinlan Add support for negotiating a subprotocol (dart-lang/http#1150)
e71e739 2024-03-05 Brian Quinlan Add `WebSocket.connect` as a cross-platform connection method (dart-lang/http#1149)
f14b5aa 2024-03-04 Brian Quinlan Include a description and version number in web_socket pubspec (dart-lang/http#1148)
5b656a9 2024-03-04 Brian Quinlan Add a LICENSE file to package:web_socket (dart-lang/http#1147)
557c420 2024-03-04 Brian Quinlan Implement WebSocket for the browser (dart-lang/http#1142)
markdown (dd47c5d..1ca5166):
1ca5166 2024-03-06 Devon Carew fix a crash when parsing alert block syntax (dart-lang/markdown#593)
package_config (4a7042b..3d90e69):
3d90e69 2024-03-05 Michael Thomsen Fix typo (dart-lang/package_config#149)
shelf (da6a69b..1acbc67):
1acbc67 2024-03-06 Andy Add shelf_router middleware examples (dart-lang/shelf#417)
vector_math (3706feb..7e705f7):
7e705f7 2024-03-06 6y Fix quaternion negate (google/vector_math.dart#316)
1ed8ac6 2024-03-06 6y Resolve Inconsistency in Matrix3 and Matrix4 `rotateY` Implementations (google/vector_math.dart#317)
web (8870d04..51e594b):
51e594b 2024-03-05 Srujan Gaddam Fix dictionary constructors to accept supertype members and create an empty object when there are no fields (dart-lang/web#197)
4af904f 2024-03-05 Srujan Gaddam Publish 0.5.1 (dart-lang/web#196)
c72ec1a 2024-03-04 Devon Carew add instructions for re-generating the package (dart-lang/web#195)
webdriver (2c1b6f8..73a7ac8):
73a7ac8 2024-03-04 dependabot[bot] Bump nanasess/setup-chromedriver from 2.2.1 to 2.2.2 (google/webdriver.dart#294)
webkit_inspection_protocol (07295b9..153fea4):
153fea4 2024-03-04 dependabot[bot] Bump nanasess/setup-chromedriver (google/webkit_inspection_protocol.dart#120)
Change-Id: Ic213677a1e2430a6de56a94e0bfaa1f33e2fc7d4
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356300
Auto-Submit: Devon Carew <devoncarew@google.com>
Reviewed-by: Konstantin Shcheglov <scheglov@google.com>
Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
Currently no globals are named, so the subsection will be empty. Three
extra bytes will be generated in the names section for the empty
subsection.
When debugging we can now name globals with the optional positional
argument:
// "my global" is new:
m.globals.define(w.GlobalType(type), "my global")
wasm-opt and v8 (d8, wami) support the subsection, so the global will
now appear as "my global" in the debugger and Wast outputs.
Change-Id: I5988ab792209c5c82593b85c48fead65ad536031
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/355120
Reviewed-by: Martin Kustermann <kustermann@google.com>
Commit-Queue: Ömer Ağacan <omersa@google.com>
Currently these two tests only passes by chance, if a `release` build
happens to be available.
R=whesse@google.com
Change-Id: I6048c6ed8ea2f299c88eaf9a6c6b2add8a03dfa0
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/356083
Auto-Submit: Morgan :) <davidmorgan@google.com>
Reviewed-by: William Hesse <whesse@google.com>
Commit-Queue: Morgan :) <davidmorgan@google.com>