diff --git a/pkg/front_end/lib/src/fasta/kernel/internal_ast.dart b/pkg/front_end/lib/src/fasta/kernel/internal_ast.dart index 0d945ade7126..25ccf51baca0 100644 --- a/pkg/front_end/lib/src/fasta/kernel/internal_ast.dart +++ b/pkg/front_end/lib/src/fasta/kernel/internal_ast.dart @@ -350,11 +350,6 @@ abstract class InternalExpression extends AuxiliaryExpression { /// Common base class for internal initializers. abstract class InternalInitializer extends AuxiliaryInitializer { - @override - void replaceChild(TreeNode child, TreeNode replacement) { - // Do nothing. The node should not be part of the resulting AST, anyway. - } - @override void visitChildren(Visitor v) => unsupported("${runtimeType}.visitChildren", -1, null); @@ -3374,6 +3369,11 @@ class ExtensionTypeRepresentationFieldInitializer extends InternalInitializer { value.parent = this; } + @override + void transformChildren(Transformer v) { + value = v.transform(value)..parent = this; + } + /// [Procedure] that represents the representation field. Procedure get field => fieldReference.asProcedure; diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart b/pkg/front_end/testcases/dart2js/issue55135.dart new file mode 100644 index 000000000000..3028be17de11 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart @@ -0,0 +1,26 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +class B implements A { + final int x = 1; +} +abstract class A { + int get x; + factory A() = B; +} + +extension type C._(A point) implements A { + C() : point = A(); // << initializer is redirecting factory +} + +void main() { + expectEquals(A().x, 1); + expectEquals(C().x, 1); +} + +expectEquals(x, y) { + if (x != y) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.strong.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.strong.expect new file mode 100644 index 000000000000..bf9f2bf77dd1 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.strong.expect @@ -0,0 +1,47 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.strong.transformed.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.strong.transformed.expect new file mode 100644 index 000000000000..bf9f2bf77dd1 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.strong.transformed.expect @@ -0,0 +1,47 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline.expect new file mode 100644 index 000000000000..7cff9fce38dd --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline.expect @@ -0,0 +1,16 @@ +class B implements A { + final int x = 1; +} + +abstract class A { + int get x; + factory A() = B; +} + +extension type C._(A point) implements A { + C() : point = A(); +} + +void main() {} + +expectEquals(x, y) {} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline_modelled.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline_modelled.expect new file mode 100644 index 000000000000..86ce38fd3fcc --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.textual_outline_modelled.expect @@ -0,0 +1,16 @@ +abstract class A { + factory A() = B; + int get x; +} + +class B implements A { + final int x = 1; +} + +expectEquals(x, y) {} + +extension type C._(A point) implements A { + C() : point = A(); +} + +void main() {} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.weak.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.expect new file mode 100644 index 000000000000..bf9f2bf77dd1 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.expect @@ -0,0 +1,47 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.weak.modular.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.modular.expect new file mode 100644 index 000000000000..bf9f2bf77dd1 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.modular.expect @@ -0,0 +1,47 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.weak.outline.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.outline.expect new file mode 100644 index 000000000000..1b030722075e --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.outline.expect @@ -0,0 +1,37 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x; + synthetic constructor •() → self::B + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ + ; +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ + ; +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void + ; +static method expectEquals(dynamic x, dynamic y) → dynamic + ; diff --git a/pkg/front_end/testcases/dart2js/issue55135.dart.weak.transformed.expect b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.transformed.expect new file mode 100644 index 000000000000..bf9f2bf77dd1 --- /dev/null +++ b/pkg/front_end/testcases/dart2js/issue55135.dart.weak.transformed.expect @@ -0,0 +1,47 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; + static method _#new#tearOff() → self::B + return new self::B::•(); +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); + static method _#new#tearOff() → self::A + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart b/pkg/front_end/testcases/extension_types/issue55135.dart new file mode 100644 index 000000000000..3028be17de11 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart @@ -0,0 +1,26 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +class B implements A { + final int x = 1; +} +abstract class A { + int get x; + factory A() = B; +} + +extension type C._(A point) implements A { + C() : point = A(); // << initializer is redirecting factory +} + +void main() { + expectEquals(A().x, 1); + expectEquals(C().x, 1); +} + +expectEquals(x, y) { + if (x != y) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.strong.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.strong.expect new file mode 100644 index 000000000000..06fe05dd71b4 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.strong.expect @@ -0,0 +1,43 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.strong.transformed.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.strong.transformed.expect new file mode 100644 index 000000000000..06fe05dd71b4 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.strong.transformed.expect @@ -0,0 +1,43 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline.expect new file mode 100644 index 000000000000..7cff9fce38dd --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline.expect @@ -0,0 +1,16 @@ +class B implements A { + final int x = 1; +} + +abstract class A { + int get x; + factory A() = B; +} + +extension type C._(A point) implements A { + C() : point = A(); +} + +void main() {} + +expectEquals(x, y) {} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline_modelled.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline_modelled.expect new file mode 100644 index 000000000000..86ce38fd3fcc --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.textual_outline_modelled.expect @@ -0,0 +1,16 @@ +abstract class A { + factory A() = B; + int get x; +} + +class B implements A { + final int x = 1; +} + +expectEquals(x, y) {} + +extension type C._(A point) implements A { + C() : point = A(); +} + +void main() {} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.weak.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.expect new file mode 100644 index 000000000000..06fe05dd71b4 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.expect @@ -0,0 +1,43 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.weak.modular.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.modular.expect new file mode 100644 index 000000000000..06fe05dd71b4 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.modular.expect @@ -0,0 +1,43 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +} diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.weak.outline.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.outline.expect new file mode 100644 index 000000000000..9ba1fd93e1fa --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.outline.expect @@ -0,0 +1,33 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x; + synthetic constructor •() → self::B + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ + ; +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ + ; +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void + ; +static method expectEquals(dynamic x, dynamic y) → dynamic + ; diff --git a/pkg/front_end/testcases/extension_types/issue55135.dart.weak.transformed.expect b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.transformed.expect new file mode 100644 index 000000000000..06fe05dd71b4 --- /dev/null +++ b/pkg/front_end/testcases/extension_types/issue55135.dart.weak.transformed.expect @@ -0,0 +1,43 @@ +library; +import self as self; +import "dart:core" as core; + +class B extends core::Object implements self::A { + final field core::int x = 1; + synthetic constructor •() → self::B + : super core::Object::•() + ; +} +abstract class A extends core::Object { + abstract get x() → core::int; + static factory •() → self::A /* redirection-target: self::B::• */ + return new self::B::•(); +} +extension type C(self::A point) implements self::A { + abstract extension-type-member representation-field get point() → self::A; + constructor _ = self::C|constructor#_; + constructor tearoff _ = self::C|constructor#_#_#tearOff; + constructor • = self::C|constructor#; + constructor tearoff • = self::C|constructor#_#new#tearOff; +} +static extension-type-member method C|constructor#_(self::A point) → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = point; + return #this; +} +static extension-type-member method C|constructor#_#_#tearOff(self::A point) → self::C /* erasure=self::A */ + return self::C|constructor#_(point); +static extension-type-member method C|constructor#() → self::C /* erasure=self::A */ { + lowered final self::C /* erasure=self::A */ #this = new self::B::•(); + return #this; +} +static extension-type-member method C|constructor#_#new#tearOff() → self::C /* erasure=self::A */ + return self::C|constructor#(); +static method main() → void { + self::expectEquals(new self::B::•().{self::A::x}{core::int}, 1); + self::expectEquals(self::C|constructor#().{self::A::x}{core::int}, 1); +} +static method expectEquals(dynamic x, dynamic y) → dynamic { + if(!(x =={core::Object::==}{(core::Object) → core::bool} y)) { + throw "Expected equal values, got '${x}' and '${y}'."; + } +}