[fasta] Fix crash when override inference depends on field inference
Change-Id: I34a273185ba09f2740783cf8a25ac6d5f754c621
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/104762
Reviewed-by: Aske Simon Christensen <askesc@google.com>
diff --git a/pkg/front_end/lib/src/fasta/kernel/class_hierarchy_builder.dart b/pkg/front_end/lib/src/fasta/kernel/class_hierarchy_builder.dart
index 5aa6fb8..040d468 100644
--- a/pkg/front_end/lib/src/fasta/kernel/class_hierarchy_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/class_hierarchy_builder.dart
@@ -911,7 +911,7 @@
debug?.log(
"${cls.fullNameForErrors} -> ${bCls.fullNameForErrors} $bSubstitution");
}
- if (bSubstitution != null) {
+ if (bSubstitution != null && inheritedType is! ImplicitFieldType) {
inheritedType = bSubstitution.substituteType(inheritedType);
}
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart
new file mode 100644
index 0000000..ebc84b6
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2019, 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 A<X> {
+ final foo = "bar";
+}
+
+class B<Y> extends A<Y> {
+ final foo;
+
+ B(this.foo);
+}
+
+main() {}
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.hierarchy.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.hierarchy.expect
new file mode 100644
index 0000000..6bb747c
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.hierarchy.expect
@@ -0,0 +1,56 @@
+Object:
+ superclasses:
+ interfaces:
+ classMembers:
+ Object._haveSameRuntimeType
+ Object.toString
+ Object.runtimeType
+ Object._toString
+ Object._simpleInstanceOf
+ Object._hashCodeRnd
+ Object._instanceOf
+ Object.noSuchMethod
+ Object._objectHashCode
+ Object._identityHashCode
+ Object.hashCode
+ Object._simpleInstanceOfFalse
+ Object._simpleInstanceOfTrue
+ Object.==
+ classSetters:
+
+A:
+ superclasses:
+ Object
+ interfaces:
+ classMembers:
+ Object.toString
+ Object.runtimeType
+ Object._simpleInstanceOf
+ Object._instanceOf
+ A.foo
+ Object.noSuchMethod
+ Object._identityHashCode
+ Object.hashCode
+ Object._simpleInstanceOfFalse
+ Object._simpleInstanceOfTrue
+ Object.==
+ classSetters:
+
+B:
+ superclasses:
+ Object
+ -> A<Y>
+ interfaces:
+ classMembers:
+ Object.toString
+ Object.runtimeType
+ Object._simpleInstanceOf
+ Object._instanceOf
+ B.foo
+ Object.noSuchMethod
+ Object._identityHashCode
+ Object.hashCode
+ Object._simpleInstanceOfFalse
+ Object._simpleInstanceOfTrue
+ Object.==
+ classSetters:
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.expect
new file mode 100644
index 0000000..d00064e
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.expect
@@ -0,0 +1,17 @@
+library;
+import self as self;
+import "dart:core" as core;
+
+class A<X extends core::Object = dynamic> extends core::Object {
+ final field dynamic foo = "bar";
+ synthetic constructor •() → self::A<self::A::X>
+ : super core::Object::•()
+ ;
+}
+class B<Y extends core::Object = dynamic> extends self::A<self::B::Y> {
+ final field dynamic foo;
+ constructor •(dynamic foo) → self::B<self::B::Y>
+ : self::B::foo = foo, super self::A::•()
+ ;
+}
+static method main() → dynamic {}
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.transformed.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.transformed.expect
new file mode 100644
index 0000000..d00064e
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.legacy.transformed.expect
@@ -0,0 +1,17 @@
+library;
+import self as self;
+import "dart:core" as core;
+
+class A<X extends core::Object = dynamic> extends core::Object {
+ final field dynamic foo = "bar";
+ synthetic constructor •() → self::A<self::A::X>
+ : super core::Object::•()
+ ;
+}
+class B<Y extends core::Object = dynamic> extends self::A<self::B::Y> {
+ final field dynamic foo;
+ constructor •(dynamic foo) → self::B<self::B::Y>
+ : self::B::foo = foo, super self::A::•()
+ ;
+}
+static method main() → dynamic {}
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.outline.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.outline.expect
new file mode 100644
index 0000000..0a5257b
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.outline.expect
@@ -0,0 +1,16 @@
+library;
+import self as self;
+import "dart:core" as core;
+
+class A<X extends core::Object = dynamic> extends core::Object {
+ final field dynamic foo;
+ synthetic constructor •() → self::A<self::A::X>
+ ;
+}
+class B<Y extends core::Object = dynamic> extends self::A<self::B::Y> {
+ final field dynamic foo;
+ constructor •(dynamic foo) → self::B<self::B::Y>
+ ;
+}
+static method main() → dynamic
+ ;
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.expect
new file mode 100644
index 0000000..faa19da
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.expect
@@ -0,0 +1,17 @@
+library;
+import self as self;
+import "dart:core" as core;
+
+class A<X extends core::Object = dynamic> extends core::Object {
+ final field core::String foo = "bar";
+ synthetic constructor •() → self::A<self::A::X>
+ : super core::Object::•()
+ ;
+}
+class B<Y extends core::Object = dynamic> extends self::A<self::B::Y> {
+ final field core::String foo;
+ constructor •(core::String foo) → self::B<self::B::Y>
+ : self::B::foo = foo, super self::A::•()
+ ;
+}
+static method main() → dynamic {}
diff --git a/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.transformed.expect b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.transformed.expect
new file mode 100644
index 0000000..faa19da
--- /dev/null
+++ b/pkg/front_end/testcases/inference/override_inference_depends_on_field_inference.dart.strong.transformed.expect
@@ -0,0 +1,17 @@
+library;
+import self as self;
+import "dart:core" as core;
+
+class A<X extends core::Object = dynamic> extends core::Object {
+ final field core::String foo = "bar";
+ synthetic constructor •() → self::A<self::A::X>
+ : super core::Object::•()
+ ;
+}
+class B<Y extends core::Object = dynamic> extends self::A<self::B::Y> {
+ final field core::String foo;
+ constructor •(core::String foo) → self::B<self::B::Y>
+ : self::B::foo = foo, super self::A::•()
+ ;
+}
+static method main() → dynamic {}
diff --git a/pkg/front_end/testcases/text_serialization.status b/pkg/front_end/testcases/text_serialization.status
index 0147dc9..43c0eb4 100644
--- a/pkg/front_end/testcases/text_serialization.status
+++ b/pkg/front_end/testcases/text_serialization.status
@@ -474,6 +474,7 @@
inference/null_literal_should_not_infer_as_bottom: TextSerializationFailure # Was: Pass
inference/overloaded_int_operators: TextSerializationFailure # Was: Pass
inference/override_equals: TextSerializationFailure # Was: RuntimeError
+inference/override_inference_depends_on_field_inference: TextSerializationFailure
inference/parameter_defaults_downwards: TextSerializationFailure # Was: Pass
inference/parameter_defaults_upwards: TextSerializationFailure # Was: Pass
inference/promote_bounds: TextSerializationFailure # Was: Pass