From 2fc9ea5ad75c00f50f2746e145cdbfa6d76ed8fd Mon Sep 17 00:00:00 2001 From: Jake Macdonald Date: Mon, 20 Mar 2023 17:29:31 +0000 Subject: [PATCH] copy language/mixin tests to language/mixin_legacy with 2.19 opt out Change-Id: Ice509ea1f0efec8153fb2380ab0e980fed552b0e Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/289580 Reviewed-by: Leaf Petersen Commit-Queue: Jake Macdonald --- .../tests/concurrency/stress_test_list.json | 2 - tests/language/mixin_legacy/README.md | 3 + .../mixin_legacy/abstract_getter_test.dart | 43 +++ .../language/mixin_legacy/accessor_test.dart | 65 ++++ .../and_extension_member_test.dart | 34 +++ .../mixin_legacy/black_listed_test.dart | 61 ++++ tests/language/mixin_legacy/bound_test.dart | 135 +++++++++ .../class_from_core_library_test.dart | 17 ++ .../cyclic_runtime_test.dart} | 19 +- tests/language/mixin_legacy/cyclic_test.dart | 33 ++ .../mixin_legacy/deduplication_test.dart | 47 +++ .../mixin_legacy/extends_field_test.dart | 124 ++++++++ .../mixin_legacy/extends_is_test.dart | 89 ++++++ .../mixin_legacy/extends_method_test.dart | 59 ++++ .../factory_constructor_test.dart | 30 ++ .../mixin_legacy/field_initializer_test.dart | 34 +++ tests/language/mixin_legacy/field_test.dart | 122 ++++++++ .../forwarding_constructor1_test.dart | 33 ++ .../forwarding_constructor2_test.dart | 32 ++ .../forwarding_constructor3_test.dart | 38 +++ .../forwarding_constructor4_test.dart | 27 ++ .../forwarding_stub_call_test.dart | 37 +++ .../forwarding_stub_set_test.dart | 37 +++ .../forwarding_stub_tearoff_test.dart | 38 +++ tests/language/mixin_legacy/generic_test.dart | 37 +++ .../mixin_legacy/getter_regression_test.dart | 32 ++ .../illegal_constructor_runtime_test.dart | 31 ++ .../illegal_constructor_test.dart | 120 ++++++++ .../mixin_legacy/illegal_cycles_test.dart | 89 ++++++ .../mixin_legacy/illegal_object_test.dart | 29 ++ .../illegal_static_access_runtime_test.dart | 25 ++ .../illegal_static_access_test.dart | 31 ++ .../illegal_super_use_runtime_test.dart | 61 ++++ .../mixin_legacy/illegal_super_use_test.dart | 91 ++++++ .../illegal_superclass_runtime_test.dart | 85 ++++++ .../mixin_legacy/illegal_superclass_test.dart | 256 ++++++++++++++++ .../mixin_legacy/illegal_syntax_test.dart | 61 ++++ .../mixin_legacy/implements2_test.dart | 19 ++ .../mixin_legacy/implements_test.dart | 79 +++++ .../implicit_covariance_test.dart | 34 +++ .../inference_mixin_field_test.dart | 30 ++ .../interface_check_runtime_test.dart | 33 ++ .../mixin_legacy/interface_check_test.dart | 33 ++ .../mixin_legacy/invalid_bound2_test.dart | 50 +++ .../mixin_legacy/invalid_bound_test.dart | 41 +++ .../invalid_inheritance1_test.dart | 13 + .../invalid_inheritance2_test.dart | 13 + ...nvalid_override_in_mixin_runtime_test.dart | 25 ++ .../invalid_override_in_mixin_test.dart | 31 ++ tests/language/mixin_legacy/is_test.dart | 85 ++++++ .../mixin_legacy/issue10216_2_test.dart | 22 ++ .../mixin_legacy/issue10216_test.dart | 35 +++ .../mixin_legacy/lib_extends_field_lib.dart | 17 ++ .../mixin_legacy/lib_extends_field_test.dart | 119 ++++++++ .../mixin_legacy/lib_extends_method_lib.dart | 30 ++ .../mixin_legacy/lib_extends_method_test.dart | 55 ++++ .../method_override_runtime_test.dart | 150 +++++++++ .../mixin_legacy/method_override_test.dart | 285 ++++++++++++++++++ tests/language/mixin_legacy/method_test.dart | 56 ++++ tests/language/mixin_legacy/mixin2_test.dart | 36 +++ tests/language/mixin_legacy/mixin3_test.dart | 53 ++++ tests/language/mixin_legacy/mixin4_test.dart | 33 ++ tests/language/mixin_legacy/mixin5_test.dart | 38 +++ tests/language/mixin_legacy/mixin6_test.dart | 38 +++ tests/language/mixin_legacy/mixin7_test.dart | 38 +++ .../mixin_legacy/mixin_bound2_test.dart | 39 +++ .../mixin_legacy/mixin_bound_test.dart | 33 ++ tests/language/mixin_legacy/mixin_test.dart | 26 ++ .../mixin_type_arguments_test.dart | 99 ++++++ .../mixin_legacy/named_constructor_test.dart | 32 ++ tests/language/mixin_legacy/naming_test.dart | 53 ++++ .../mixin_legacy/only_for_rti_test.dart | 31 ++ .../override_regression_test.dart | 27 ++ tests/language/mixin_legacy/prefix_lib.dart | 13 + tests/language/mixin_legacy/prefix_test.dart | 19 ++ tests/language/mixin_legacy/proto_test.dart | 42 +++ .../mixin_legacy/recursive_mixin_test.dart | 28 ++ .../mixin_legacy/regress_11398_test.dart | 46 +++ .../mixin_legacy/regress_13688_test.dart | 20 ++ .../mixin_legacy/regress_47645_test.dart | 21 ++ .../regress_flutter_55345_const_test.dart | 40 +++ .../regress_flutter_55345_test.dart | 44 +++ .../regress_flutter_66859_1_test.dart | 33 ++ .../regress_flutter_66859_2_test.dart | 39 +++ .../mixin_legacy/substitution_test.dart | 28 ++ tests/language/mixin_legacy/super_2_test.dart | 43 +++ .../super_bound_runtime_test.dart | 30 ++ .../mixin_legacy/super_bound_test.dart | 37 +++ .../mixin_legacy/super_constructor2_test.dart | 41 +++ .../super_constructor_default_test.dart | 33 ++ .../super_constructor_multiple_test.dart | 24 ++ .../super_constructor_named_test.dart | 41 +++ .../super_constructor_positionals_test.dart | 40 +++ .../mixin_legacy/super_constructor_test.dart | 33 ++ tests/language/mixin_legacy/super_test.dart | 106 +++++++ .../language/mixin_legacy/super_use_test.dart | 67 ++++ .../super_with_initializer_test.dart | 32 ++ .../mixin_legacy/superclass_runtime_test.dart | 94 ++++++ .../mixin_legacy/superclass_test.dart | 220 ++++++++++++++ .../supertype_subclass2_test.dart | 30 ++ .../mixin_legacy/supertype_subclass_test.dart | 30 ++ .../language/mixin_legacy/this_use_test.dart | 32 ++ .../mixin_legacy/type_parameter1_test.dart | 25 ++ .../mixin_legacy/type_parameter2_test.dart | 29 ++ .../mixin_legacy/type_parameter3_test.dart | 27 ++ .../mixin_legacy/type_parameter4_test.dart | 26 ++ .../mixin_legacy/type_parameter5_test.dart | 28 ++ .../mixin_legacy/type_parameter6_test.dart | 19 ++ .../type_parameter_inference_error_test.dart | 26 ++ ...rameter_inference_previous_mixin_test.dart | 39 +++ .../type_parameter_inference_test.dart | 75 +++++ .../type_parameters_errors_runtime_test.dart} | 38 +-- .../type_parameters_errors_test.dart | 45 +++ .../type_parameters_mixin_extends_test.dart | 132 ++++++++ .../type_parameters_mixin_test.dart | 129 ++++++++ .../type_parameters_simple_test.dart | 31 ++ .../type_parameters_super_extends_test.dart | 132 ++++++++ .../type_parameters_super_test.dart | 100 ++++++ .../mixin_legacy/type_variable_test.dart | 34 +++ .../typedef_constructor_test.dart | 24 ++ .../mixin_legacy/with_named_import_test.dart | 18 ++ .../with_two_implicit_constructors_test.dart | 22 ++ 122 files changed, 6206 insertions(+), 37 deletions(-) create mode 100644 tests/language/mixin_legacy/README.md create mode 100644 tests/language/mixin_legacy/abstract_getter_test.dart create mode 100644 tests/language/mixin_legacy/accessor_test.dart create mode 100644 tests/language/mixin_legacy/and_extension_member_test.dart create mode 100644 tests/language/mixin_legacy/black_listed_test.dart create mode 100644 tests/language/mixin_legacy/bound_test.dart create mode 100644 tests/language/mixin_legacy/class_from_core_library_test.dart rename tests/language/{mixin/illegal_object_runtime_test.dart => mixin_legacy/cyclic_runtime_test.dart} (52%) create mode 100644 tests/language/mixin_legacy/cyclic_test.dart create mode 100644 tests/language/mixin_legacy/deduplication_test.dart create mode 100644 tests/language/mixin_legacy/extends_field_test.dart create mode 100644 tests/language/mixin_legacy/extends_is_test.dart create mode 100644 tests/language/mixin_legacy/extends_method_test.dart create mode 100644 tests/language/mixin_legacy/factory_constructor_test.dart create mode 100644 tests/language/mixin_legacy/field_initializer_test.dart create mode 100644 tests/language/mixin_legacy/field_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_constructor1_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_constructor2_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_constructor3_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_constructor4_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_stub_call_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_stub_set_test.dart create mode 100644 tests/language/mixin_legacy/forwarding_stub_tearoff_test.dart create mode 100644 tests/language/mixin_legacy/generic_test.dart create mode 100644 tests/language/mixin_legacy/getter_regression_test.dart create mode 100644 tests/language/mixin_legacy/illegal_constructor_runtime_test.dart create mode 100644 tests/language/mixin_legacy/illegal_constructor_test.dart create mode 100644 tests/language/mixin_legacy/illegal_cycles_test.dart create mode 100644 tests/language/mixin_legacy/illegal_object_test.dart create mode 100644 tests/language/mixin_legacy/illegal_static_access_runtime_test.dart create mode 100644 tests/language/mixin_legacy/illegal_static_access_test.dart create mode 100644 tests/language/mixin_legacy/illegal_super_use_runtime_test.dart create mode 100644 tests/language/mixin_legacy/illegal_super_use_test.dart create mode 100644 tests/language/mixin_legacy/illegal_superclass_runtime_test.dart create mode 100644 tests/language/mixin_legacy/illegal_superclass_test.dart create mode 100644 tests/language/mixin_legacy/illegal_syntax_test.dart create mode 100644 tests/language/mixin_legacy/implements2_test.dart create mode 100644 tests/language/mixin_legacy/implements_test.dart create mode 100644 tests/language/mixin_legacy/implicit_covariance_test.dart create mode 100644 tests/language/mixin_legacy/inference_mixin_field_test.dart create mode 100644 tests/language/mixin_legacy/interface_check_runtime_test.dart create mode 100644 tests/language/mixin_legacy/interface_check_test.dart create mode 100644 tests/language/mixin_legacy/invalid_bound2_test.dart create mode 100644 tests/language/mixin_legacy/invalid_bound_test.dart create mode 100644 tests/language/mixin_legacy/invalid_inheritance1_test.dart create mode 100644 tests/language/mixin_legacy/invalid_inheritance2_test.dart create mode 100644 tests/language/mixin_legacy/invalid_override_in_mixin_runtime_test.dart create mode 100644 tests/language/mixin_legacy/invalid_override_in_mixin_test.dart create mode 100644 tests/language/mixin_legacy/is_test.dart create mode 100644 tests/language/mixin_legacy/issue10216_2_test.dart create mode 100644 tests/language/mixin_legacy/issue10216_test.dart create mode 100644 tests/language/mixin_legacy/lib_extends_field_lib.dart create mode 100644 tests/language/mixin_legacy/lib_extends_field_test.dart create mode 100644 tests/language/mixin_legacy/lib_extends_method_lib.dart create mode 100644 tests/language/mixin_legacy/lib_extends_method_test.dart create mode 100644 tests/language/mixin_legacy/method_override_runtime_test.dart create mode 100644 tests/language/mixin_legacy/method_override_test.dart create mode 100644 tests/language/mixin_legacy/method_test.dart create mode 100644 tests/language/mixin_legacy/mixin2_test.dart create mode 100644 tests/language/mixin_legacy/mixin3_test.dart create mode 100644 tests/language/mixin_legacy/mixin4_test.dart create mode 100644 tests/language/mixin_legacy/mixin5_test.dart create mode 100644 tests/language/mixin_legacy/mixin6_test.dart create mode 100644 tests/language/mixin_legacy/mixin7_test.dart create mode 100644 tests/language/mixin_legacy/mixin_bound2_test.dart create mode 100644 tests/language/mixin_legacy/mixin_bound_test.dart create mode 100644 tests/language/mixin_legacy/mixin_test.dart create mode 100644 tests/language/mixin_legacy/mixin_type_arguments_test.dart create mode 100644 tests/language/mixin_legacy/named_constructor_test.dart create mode 100644 tests/language/mixin_legacy/naming_test.dart create mode 100644 tests/language/mixin_legacy/only_for_rti_test.dart create mode 100644 tests/language/mixin_legacy/override_regression_test.dart create mode 100644 tests/language/mixin_legacy/prefix_lib.dart create mode 100644 tests/language/mixin_legacy/prefix_test.dart create mode 100644 tests/language/mixin_legacy/proto_test.dart create mode 100644 tests/language/mixin_legacy/recursive_mixin_test.dart create mode 100644 tests/language/mixin_legacy/regress_11398_test.dart create mode 100644 tests/language/mixin_legacy/regress_13688_test.dart create mode 100644 tests/language/mixin_legacy/regress_47645_test.dart create mode 100644 tests/language/mixin_legacy/regress_flutter_55345_const_test.dart create mode 100644 tests/language/mixin_legacy/regress_flutter_55345_test.dart create mode 100644 tests/language/mixin_legacy/regress_flutter_66859_1_test.dart create mode 100644 tests/language/mixin_legacy/regress_flutter_66859_2_test.dart create mode 100644 tests/language/mixin_legacy/substitution_test.dart create mode 100644 tests/language/mixin_legacy/super_2_test.dart create mode 100644 tests/language/mixin_legacy/super_bound_runtime_test.dart create mode 100644 tests/language/mixin_legacy/super_bound_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor2_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor_default_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor_multiple_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor_named_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor_positionals_test.dart create mode 100644 tests/language/mixin_legacy/super_constructor_test.dart create mode 100644 tests/language/mixin_legacy/super_test.dart create mode 100644 tests/language/mixin_legacy/super_use_test.dart create mode 100644 tests/language/mixin_legacy/super_with_initializer_test.dart create mode 100644 tests/language/mixin_legacy/superclass_runtime_test.dart create mode 100644 tests/language/mixin_legacy/superclass_test.dart create mode 100644 tests/language/mixin_legacy/supertype_subclass2_test.dart create mode 100644 tests/language/mixin_legacy/supertype_subclass_test.dart create mode 100644 tests/language/mixin_legacy/this_use_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter1_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter2_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter3_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter4_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter5_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter6_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter_inference_error_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter_inference_previous_mixin_test.dart create mode 100644 tests/language/mixin_legacy/type_parameter_inference_test.dart rename tests/language/{mixin/illegal_cycles_runtime_test.dart => mixin_legacy/type_parameters_errors_runtime_test.dart} (53%) create mode 100644 tests/language/mixin_legacy/type_parameters_errors_test.dart create mode 100644 tests/language/mixin_legacy/type_parameters_mixin_extends_test.dart create mode 100644 tests/language/mixin_legacy/type_parameters_mixin_test.dart create mode 100644 tests/language/mixin_legacy/type_parameters_simple_test.dart create mode 100644 tests/language/mixin_legacy/type_parameters_super_extends_test.dart create mode 100644 tests/language/mixin_legacy/type_parameters_super_test.dart create mode 100644 tests/language/mixin_legacy/type_variable_test.dart create mode 100644 tests/language/mixin_legacy/typedef_constructor_test.dart create mode 100644 tests/language/mixin_legacy/with_named_import_test.dart create mode 100644 tests/language/mixin_legacy/with_two_implicit_constructors_test.dart diff --git a/runtime/tests/concurrency/stress_test_list.json b/runtime/tests/concurrency/stress_test_list.json index 1f4de6c3d6d..6984088818b 100644 --- a/runtime/tests/concurrency/stress_test_list.json +++ b/runtime/tests/concurrency/stress_test_list.json @@ -1652,8 +1652,6 @@ "../../../tests/language/mixin/generic_test.dart", "../../../tests/language/mixin/getter_regression_test.dart", "../../../tests/language/mixin/illegal_constructor_runtime_test.dart", - "../../../tests/language/mixin/illegal_cycles_runtime_test.dart", - "../../../tests/language/mixin/illegal_object_runtime_test.dart", "../../../tests/language/mixin/illegal_static_access_runtime_test.dart", "../../../tests/language/mixin/illegal_super_use_runtime_test.dart", "../../../tests/language/mixin/illegal_superclass_runtime_test.dart", diff --git a/tests/language/mixin_legacy/README.md b/tests/language/mixin_legacy/README.md new file mode 100644 index 00000000000..5f00498d256 --- /dev/null +++ b/tests/language/mixin_legacy/README.md @@ -0,0 +1,3 @@ +Tests for pre Dart 3.0 behavior of mixins. + +Delete this when 2.19 is no longer supported. diff --git a/tests/language/mixin_legacy/abstract_getter_test.dart b/tests/language/mixin_legacy/abstract_getter_test.dart new file mode 100644 index 00000000000..564c5901207 --- /dev/null +++ b/tests/language/mixin_legacy/abstract_getter_test.dart @@ -0,0 +1,43 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'package:expect/expect.dart'; + +abstract class B { + int get x; +} + +class C { + int get x => 42; +} + +class D extends C with B { + final int x; + + D(this.x); +} + +class C2 { + int get x => 42; +} + +abstract class B2 extends C2 { + int get x; +} + +class D2 extends B2 { + final int x; + + D2(this.x); +} + +void main() { + var d = new D(17); + Expect.equals(d.x, 17); + + var d2 = new D2(17); + Expect.equals(d.x, 17); +} diff --git a/tests/language/mixin_legacy/accessor_test.dart b/tests/language/mixin_legacy/accessor_test.dart new file mode 100644 index 00000000000..2955258e9e0 --- /dev/null +++ b/tests/language/mixin_legacy/accessor_test.dart @@ -0,0 +1,65 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Regression test case for DDC bug where if a getter/setter is mixed in +// without a corresponding getter/setter, DDC fails to install a the +// corresponding getter/setter that calls super. + +import "package:expect/expect.dart"; + +abstract class C { + E get first; + set first(E value); + E operator [](int index); + operator []=(int index, E value); +} + +abstract class CMixin implements C { + E get first => this[0]; + set first(E x) { + this[0] = x; + } +} + +abstract class CBase extends Object with CMixin {} + +abstract class DMixin implements C { + set first(E _) => throw new UnsupportedError(''); + operator []=(int index, E value) => throw new UnsupportedError(''); +} + +abstract class DBase = CBase with DMixin; + +class DView extends DBase { + final Iterable _source; + DView(this._source); + E operator [](int index) => _source.elementAt(index); +} + +abstract class FMixin implements C { + E get first => throw new UnsupportedError(''); + E operator [](int index) => throw new UnsupportedError(''); +} + +class FView extends CBase with FMixin { + List _values; + FView(this._values); + operator []=(int index, E value) { + _values[index] = value; + } +} + +void main() { + var d = new DView([3]); + Expect.equals(3, d.first); + Expect.throws(() => d.first = 42, (e) => e is UnsupportedError); + + var list = [3]; + var f = new FView(list); + f.first = 42; + Expect.equals(42, list[0]); + Expect.throws(() => f.first, (e) => e is UnsupportedError); +} diff --git a/tests/language/mixin_legacy/and_extension_member_test.dart b/tests/language/mixin_legacy/and_extension_member_test.dart new file mode 100644 index 00000000000..4fa55fe4eb5 --- /dev/null +++ b/tests/language/mixin_legacy/and_extension_member_test.dart @@ -0,0 +1,34 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'dart:collection'; +import 'package:expect/expect.dart'; + +class OverrideFirstGetter { + get first => 9999; +} + +class ListMock extends ListBase with OverrideFirstGetter { + final _list = []; + int get length => _list.length; + void set length(int x) { + _list.length = x; + } + + operator [](x) => _list[x]; + void operator []=(x, y) { + _list[x] = y; + } +} + +// Regression test for +// https://github.com/dart-lang/sdk/issues/29273#issuecomment-292384130 +main() { + List x = new ListMock(); + x.add(42); + Expect.equals(42, x[0]); + Expect.equals(9999, x.first); +} diff --git a/tests/language/mixin_legacy/black_listed_test.dart b/tests/language/mixin_legacy/black_listed_test.dart new file mode 100644 index 00000000000..5dc50885a15 --- /dev/null +++ b/tests/language/mixin_legacy/black_listed_test.dart @@ -0,0 +1,61 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Check mixin of black-listed types. + +import 'package:expect/expect.dart'; + +class C {} + +class D {} + +class C1 extends Object +with String //# 01: compile-time error +{} + +class D1 extends Object with C +, Null //# 02: compile-time error +{} + +class E1 extends Object + with +int, //# 03: compile-time error + C {} + +class F1 extends Object + with + C +, double //# 04: compile-time error + , + D {} + +class C2 = Object with num; //# 05: compile-time error + +class D2 = Object with C +, bool //# 06: compile-time error + ; + +class E2 = Object + with +String, //# 07: compile-time error + C; + +class F2 = Object + with + C, +dynamic, //# 08: compile-time error + D; + +main() { + Expect.isNotNull(new C1()); + Expect.isNotNull(new D1()); + Expect.isNotNull(new E1()); + Expect.isNotNull(new F1()); + Expect.isNotNull(new C2()); //# 05: continued + Expect.isNotNull(new D2()); + Expect.isNotNull(new E2()); + Expect.isNotNull(new F2()); +} diff --git a/tests/language/mixin_legacy/bound_test.dart b/tests/language/mixin_legacy/bound_test.dart new file mode 100644 index 00000000000..1a07e59510e --- /dev/null +++ b/tests/language/mixin_legacy/bound_test.dart @@ -0,0 +1,135 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +// library abstract_expressions; + +abstract class AbstractExpression {} + +abstract class AbstractAddition { + E operand1, operand2; + AbstractAddition(this.operand1, this.operand2); +} + +abstract class AbstractSubtraction { + E operand1, operand2; + AbstractSubtraction(this.operand1, this.operand2); +} + +abstract class AbstractNumber { + int val; + AbstractNumber(this.val); +} + +// library evaluator; + +abstract class ExpressionWithEval { + int get eval; +} + +abstract class AdditionWithEval { + E get operand1; + E get operand2; + int get eval => operand1.eval + operand2.eval; +} + +abstract class SubtractionWithEval { + E get operand1; + E get operand2; + int get eval => operand1.eval - operand2.eval; +} + +abstract class NumberWithEval { + int get val; + int get eval => val; +} + +// library multiplication; + +abstract class AbstractMultiplication { + E operand1, operand2; + AbstractMultiplication(this.operand1, this.operand2); +} + +// library multiplicationEvaluator; + +// import 'evaluator.dart' show ExpressionWithEval; + +abstract class MultiplicationWithEval { + E get operand1; + E get operand2; + int get eval => operand1.eval * operand2.eval; +} + +// library string_converter; + +abstract class ExpressionWithStringConversion { + String toString(); +} + +abstract class AdditionWithStringConversion< + E extends ExpressionWithStringConversion> { + E get operand1; + E get operand2; + String toString() => '($operand1 + $operand2))'; +} + +abstract class SubtractionWithStringConversion< + E extends ExpressionWithStringConversion> { + E get operand1; + E get operand2; + String toString() => '($operand1 - $operand2)'; +} + +abstract class NumberWithStringConversion { + int get val; + String toString() => val.toString(); +} + +abstract class MultiplicationWithStringConversion< + E extends ExpressionWithStringConversion> { + E get operand1; + E get operand2; + String toString() => '($operand1 * $operand2)'; +} + +// library expressions; + +// import 'abstractExpressions.dart'; +// import 'evaluator.dart'; +// import 'multiplication.dart'; +// import 'multiplicationEvaluator.dart'; +// import 'stringConverter.dart'; + +abstract class Expression = AbstractExpression + with ExpressionWithEval, ExpressionWithStringConversion; + +class Addition = AbstractAddition + with AdditionWithEval, AdditionWithStringConversion + implements Expression; + +class Subtraction = AbstractSubtraction + with + SubtractionWithEval, + SubtractionWithStringConversion + implements Expression; + +class Number = AbstractNumber + with NumberWithEval, NumberWithStringConversion + implements Expression; + +class Multiplication = AbstractMultiplication + with + MultiplicationWithEval, + MultiplicationWithStringConversion + implements Expression; + +void main() { + Expression e = new Multiplication(new Addition(new Number(4), new Number(2)), + new Subtraction(new Number(10), new Number(7))); + Expect.equals('((4 + 2)) * (10 - 7)) = 18', '$e = ${e.eval}'); +} diff --git a/tests/language/mixin_legacy/class_from_core_library_test.dart b/tests/language/mixin_legacy/class_from_core_library_test.dart new file mode 100644 index 00000000000..5f27385a165 --- /dev/null +++ b/tests/language/mixin_legacy/class_from_core_library_test.dart @@ -0,0 +1,17 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'dart:collection'; + +class MyList extends Object with ListMixin { + int length = 0; + operator [](index) => null; + void operator []=(index, value) {} +} + +main() { + new MyList().length; +} diff --git a/tests/language/mixin/illegal_object_runtime_test.dart b/tests/language/mixin_legacy/cyclic_runtime_test.dart similarity index 52% rename from tests/language/mixin/illegal_object_runtime_test.dart rename to tests/language/mixin_legacy/cyclic_runtime_test.dart index 9f8bf276174..310c8247da5 100644 --- a/tests/language/mixin/illegal_object_runtime_test.dart +++ b/tests/language/mixin_legacy/cyclic_runtime_test.dart @@ -1,21 +1,26 @@ // TODO(multitest): This was automatically migrated from a multitest and may // contain strange or dead code. -// Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file +// Copyright (c) 2023, 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. -// Object has a non-trivial constructor and hence cannot be used as mixin. +// @dart=2.19 + +// Test for cyclicity check on named mixin applications. + +class A {} class S {} -class C0 extends S +class M {} -{} +class C1 = S with M; +class C3 = S with M implements A; +void main() { + new C1(); -main() { - new C0(); - + new C3(); } diff --git a/tests/language/mixin_legacy/cyclic_test.dart b/tests/language/mixin_legacy/cyclic_test.dart new file mode 100644 index 00000000000..a318358ebb1 --- /dev/null +++ b/tests/language/mixin_legacy/cyclic_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test for cyclicity check on named mixin applications. + +class A {} + +class S {} + +class M {} + +class C1 = S with M; +class C2 = S with C2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'C2' is a supertype of itself. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +class C3 = S with M implements A; +class C4 = S with M implements C4; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'C4' is a supertype of itself. + +void main() { + new C1(); + new C2(); + new C3(); + new C4(); +} diff --git a/tests/language/mixin_legacy/deduplication_test.dart b/tests/language/mixin_legacy/deduplication_test.dart new file mode 100644 index 00000000000..0952f329f0e --- /dev/null +++ b/tests/language/mixin_legacy/deduplication_test.dart @@ -0,0 +1,47 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test mixin de-duplication with new mixin syntax. + +import 'package:expect/expect.dart'; + +class A { + int foo() => 1; +} + +class B { + int bar() => 2; +} + +abstract class C implements A, B {} + +mixin M1 on A, B { + int sum() => foo() + bar(); +} + +mixin M2 on A, B, M1 { + int sumX2() => sum() * 2; +} + +class X extends C with M1, M2 { + int foo() => 4; + int bar() => 5; +} + +class Y extends C with M1, M2 { + int foo() => 7; + int bar() => 10; +} + +X x = new X(); +Y y = new Y(); + +void main() { + Expect.equals(9, x.sum()); + Expect.equals(18, x.sumX2()); + Expect.equals(17, y.sum()); + Expect.equals(34, y.sumX2()); +} diff --git a/tests/language/mixin_legacy/extends_field_test.dart b/tests/language/mixin_legacy/extends_field_test.dart new file mode 100644 index 00000000000..b97612b6c52 --- /dev/null +++ b/tests/language/mixin_legacy/extends_field_test.dart @@ -0,0 +1,124 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + var foo = "S-foo"; +} + +class M1 { + final bar = "M1-bar"; +} + +class M2 { + var baz = "M2-baz"; +} + +class C extends S with M1 {} + +class D extends S with M1, M2 {} + +class E extends S with M2, M1 {} + +class F extends E { + var fez = "F-fez"; +} + +main() { + dynamic c = new C(); + dynamic d = new D(); + dynamic e = new E(); + dynamic f = new F(); + + Expect.equals("S-foo", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez", f.fez); + + c.foo = "S-foo-c"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + d.foo = "S-foo-d"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + e.foo = "S-foo-e"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo", f.foo); + + f.foo = "S-foo-f"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo-f", f.foo); + + Expect.throwsNoSuchMethodError(() => c.bar = 0); + Expect.throwsNoSuchMethodError(() => d.bar = 0); + Expect.throwsNoSuchMethodError(() => e.bar = 0); + Expect.throwsNoSuchMethodError(() => f.bar = 0); + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz = 0); + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + d.baz = "M2-baz-d"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + Expect.equals("M2-baz", f.baz); + + e.baz = "M2-baz-e"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz", f.baz); + + f.baz = "M2-baz-f"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz-f", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez = 0); + Expect.throwsNoSuchMethodError(() => d.fez = 0); + Expect.throwsNoSuchMethodError(() => e.fez = 0); + + f.fez = "F-fez-f"; + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez-f", f.fez); +} diff --git a/tests/language/mixin_legacy/extends_is_test.dart b/tests/language/mixin_legacy/extends_is_test.dart new file mode 100644 index 00000000000..9c1b52099e6 --- /dev/null +++ b/tests/language/mixin_legacy/extends_is_test.dart @@ -0,0 +1,89 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S {} + +class M1 {} + +class M2 {} + +class C extends S with M1 {} + +class D extends S with M1, M2 {} + +class E extends S with M2, M1 {} + +class F extends E {} + +class C_ extends S with M1 {} + +class D_ extends S with M1, M2 {} + +class E_ extends S with M2, M1 {} + +class F_ extends E_ {} + +main() { + var c = new C(); + Expect.isTrue(c is C); + Expect.isFalse(c is D); + Expect.isFalse(c is E); + Expect.isFalse(c is F); + Expect.isTrue(c is S); + Expect.isTrue(c is M1); + Expect.isFalse(c is M2); + + var d = new D(); + Expect.isFalse(d is C); + Expect.isTrue(d is D); + Expect.isFalse(d is E); + Expect.isFalse(d is F); + Expect.isTrue(d is S); + Expect.isTrue(d is M1); + Expect.isTrue(d is M2); + + var e = new E(); + Expect.isFalse(e is C); + Expect.isFalse(e is D); + Expect.isTrue(e is E); + Expect.isFalse(e is F); + Expect.isTrue(e is S); + Expect.isTrue(e is M1); + Expect.isTrue(e is M2); + + var f = new F(); + Expect.isFalse(f is C); + Expect.isFalse(f is D); + Expect.isTrue(f is E); + Expect.isTrue(f is F); + Expect.isTrue(f is S); + Expect.isTrue(f is M1); + Expect.isTrue(f is M2); + + // Make sure we get a new class for each mixin + // application (at least the named ones). + Expect.isFalse(c is C_); + Expect.isFalse(c is D_); + Expect.isFalse(c is E_); + Expect.isFalse(c is F_); + + Expect.isFalse(d is C_); + Expect.isFalse(d is D_); + Expect.isFalse(d is E_); + Expect.isFalse(d is F_); + + Expect.isFalse(e is C_); + Expect.isFalse(e is D_); + Expect.isFalse(e is E_); + Expect.isFalse(e is F_); + + Expect.isFalse(f is C_); + Expect.isFalse(f is D_); + Expect.isFalse(f is E_); + Expect.isFalse(f is F_); +} diff --git a/tests/language/mixin_legacy/extends_method_test.dart b/tests/language/mixin_legacy/extends_method_test.dart new file mode 100644 index 00000000000..470f40af0a0 --- /dev/null +++ b/tests/language/mixin_legacy/extends_method_test.dart @@ -0,0 +1,59 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + foo() => "S-foo"; + baz() => "S-baz"; +} + +class M1 { + static m1bar() => "M1-bar"; + bar() => m1bar(); +} + +class M2 { + bar() => "M2-bar"; + baz() => "M2-baz"; + fez() => "M2-fez"; +} + +class C extends S with M1 {} + +class D extends S with M1, M2 {} + +class E extends S with M2, M1 {} + +class F extends E { + fez() => "F-fez"; +} + +main() { + dynamic c = new C(); + Expect.equals("S-foo", c.foo()); + Expect.equals("M1-bar", c.bar()); + Expect.equals("S-baz", c.baz()); + Expect.throwsNoSuchMethodError(() => c.fez()); + + var d = new D(); + Expect.equals("S-foo", d.foo()); + Expect.equals("M2-bar", d.bar()); + Expect.equals("M2-baz", d.baz()); + Expect.equals("M2-fez", d.fez()); + + var e = new E(); + Expect.equals("S-foo", e.foo()); + Expect.equals("M1-bar", e.bar()); + Expect.equals("M2-baz", e.baz()); + Expect.equals("M2-fez", e.fez()); + + var f = new F(); + Expect.equals("S-foo", f.foo()); + Expect.equals("M1-bar", f.bar()); + Expect.equals("M2-baz", f.baz()); + Expect.equals("F-fez", f.fez()); +} diff --git a/tests/language/mixin_legacy/factory_constructor_test.dart b/tests/language/mixin_legacy/factory_constructor_test.dart new file mode 100644 index 00000000000..afd9f55f394 --- /dev/null +++ b/tests/language/mixin_legacy/factory_constructor_test.dart @@ -0,0 +1,30 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + var y; + Base._() { + y = "world"; + } +} + +abstract class Mixin implements Base { + final x = "hello"; + factory Mixin() => new _MixinAndBase._(); +} + +// TODO(jmesserly): according to the spec, this does not appear to be a valid +// mixin (because it declares a constructor), however it is supported by Dart +// implementations. +class _MixinAndBase = Base with Mixin; + +void main() { + var val = new Mixin(); + Expect.equals(val.x, "hello"); + Expect.equals(val.y, "world"); +} diff --git a/tests/language/mixin_legacy/field_initializer_test.dart b/tests/language/mixin_legacy/field_initializer_test.dart new file mode 100644 index 00000000000..f04228fffa4 --- /dev/null +++ b/tests/language/mixin_legacy/field_initializer_test.dart @@ -0,0 +1,34 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Dart test program for testing throw statement + +import 'package:expect/expect.dart'; + +class S { + var s1 = good_stuff(); + static good_stuff() => "Speyburn"; +} + +good_stuff() => "Glenfiddich"; + +class M { + var m1 = good_stuff(); + static good_stuff() => "Macallen"; +} + +class A extends S with M { + static good_stuff() => "Ardberg"; +} + +main() { + var a = new A(); + Expect.equals("Macallen", a.m1); + Expect.equals("Speyburn", a.s1); + + var m = new M(); + Expect.equals("Macallen", m.m1); +} diff --git a/tests/language/mixin_legacy/field_test.dart b/tests/language/mixin_legacy/field_test.dart new file mode 100644 index 00000000000..a66497392c9 --- /dev/null +++ b/tests/language/mixin_legacy/field_test.dart @@ -0,0 +1,122 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + var foo = "S-foo"; +} + +class M1 { + final bar = "M1-bar"; +} + +class M2 { + var baz = "M2-baz"; +} + +class C = S with M1; +class D = S with M1, M2; +class E = S with M2, M1; + +class F extends E { + var fez = "F-fez"; +} + +main() { + dynamic c = new C(); + dynamic d = new D(); + dynamic e = new E(); + dynamic f = new F(); + + Expect.equals("S-foo", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez", f.fez); + + c.foo = "S-foo-c"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + d.foo = "S-foo-d"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + e.foo = "S-foo-e"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo", f.foo); + + f.foo = "S-foo-f"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo-f", f.foo); + + Expect.throwsNoSuchMethodError(() => c.bar = 0); + Expect.throwsNoSuchMethodError(() => d.bar = 0); + Expect.throwsNoSuchMethodError(() => e.bar = 0); + Expect.throwsNoSuchMethodError(() => f.bar = 0); + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz = 0); + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + d.baz = "M2-baz-d"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + Expect.equals("M2-baz", f.baz); + + e.baz = "M2-baz-e"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz", f.baz); + + f.baz = "M2-baz-f"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz-f", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez = 0); + Expect.throwsNoSuchMethodError(() => d.fez = 0); + Expect.throwsNoSuchMethodError(() => e.fez = 0); + + f.fez = "F-fez-f"; + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez-f", f.fez); +} diff --git a/tests/language/mixin_legacy/forwarding_constructor1_test.dart b/tests/language/mixin_legacy/forwarding_constructor1_test.dart new file mode 100644 index 00000000000..b9910afcdd7 --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_constructor1_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class Mixin1 { + var mixin1Field = 1; +} + +abstract class Mixin2 { + var mixin2Field = 2; +} + +class A { + var superField; + A(foo) : superField = foo; +} + +class B extends A with Mixin1, Mixin2 { + var field = 4; + B(unused) : super(3); +} + +main() { + var b = new B(null); + Expect.equals(1, b.mixin1Field); + Expect.equals(2, b.mixin2Field); + Expect.equals(3, b.superField); + Expect.equals(4, b.field); +} diff --git a/tests/language/mixin_legacy/forwarding_constructor2_test.dart b/tests/language/mixin_legacy/forwarding_constructor2_test.dart new file mode 100644 index 00000000000..af7b986b761 --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_constructor2_test.dart @@ -0,0 +1,32 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class Mixin1 { + var mixin1Field = 1; +} + +abstract class Mixin2 { + var mixin2Field = 2; +} + +class A { + var superField; + A() : superField = 3; +} + +class B extends A with Mixin1, Mixin2 { + var field = 4; +} + +main() { + var b = new B(); + Expect.equals(1, b.mixin1Field); + Expect.equals(2, b.mixin2Field); + Expect.equals(3, b.superField); + Expect.equals(4, b.field); +} diff --git a/tests/language/mixin_legacy/forwarding_constructor3_test.dart b/tests/language/mixin_legacy/forwarding_constructor3_test.dart new file mode 100644 index 00000000000..e690171b33b --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_constructor3_test.dart @@ -0,0 +1,38 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verify that a named mixin constructor forwards to the corresponding named +// base class constructor. + +import "package:expect/expect.dart"; + +abstract class Mixin1 { + var mixin1Field = 1; +} + +abstract class Mixin2 { + var mixin2Field = 2; +} + +class A { + var superField; + A(foo) : superField = 0; + A.c1(foo) : superField = foo; + A.c2(foo) : superField = 0; +} + +class B extends A with Mixin1, Mixin2 { + var field = 4; + B(unused) : super.c1(3); +} + +main() { + var b = new B(null); + Expect.equals(1, b.mixin1Field); + Expect.equals(2, b.mixin2Field); + Expect.equals(3, b.superField); + Expect.equals(4, b.field); +} diff --git a/tests/language/mixin_legacy/forwarding_constructor4_test.dart b/tests/language/mixin_legacy/forwarding_constructor4_test.dart new file mode 100644 index 00000000000..d41957821b2 --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_constructor4_test.dart @@ -0,0 +1,27 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verify that a forwarding constructor is generated even when there is an +// optional parameter. + +abstract class Mixin {} + +class Base { + Base( + {x} // //# 01: ok + {x} // //# 02: ok + {x} // //# 03: ok + ); +} + +class C extends Base with Mixin { + C(); // //# 02: continued + C() : super(); //# 03: continued +} + +main() { + new C(); +} diff --git a/tests/language/mixin_legacy/forwarding_stub_call_test.dart b/tests/language/mixin_legacy/forwarding_stub_call_test.dart new file mode 100644 index 00000000000..24c8a3b17b2 --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_stub_call_test.dart @@ -0,0 +1,37 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test for calling a method for which a forwarding super stub has been +// inserted. + +import 'package:expect/expect.dart'; + +class Super { + void method(T t) {} +} + +class Mixin { + void method(int t) {} +} + +// A forwarding super stub is inserted: +// +// void method(/*generic-covariant-impl*/ int t) => super.method(t); +// +class Class = Super with Mixin; + +class Subclass extends Class { + void test() { + // Test that we can call the method. + super.method(0); + } +} + +main() { + Super s = new Subclass()..test(); + // Test that the covariance check is performed. + Expect.throws(() => s.method('')); +} diff --git a/tests/language/mixin_legacy/forwarding_stub_set_test.dart b/tests/language/mixin_legacy/forwarding_stub_set_test.dart new file mode 100644 index 00000000000..f9923d8af8d --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_stub_set_test.dart @@ -0,0 +1,37 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test for assigning to a field for which a forwarding super stub has been +// inserted. + +import 'package:expect/expect.dart'; + +class Super { + T? field; +} + +class Mixin { + int? field; +} + +// A forwarding super stub is inserted: +// +// void set field(/*generic-covariant-impl*/ int t) => super.field = t; +// +class Class = Super with Mixin; + +class Subclass extends Class { + void test() { + // Test that we can perform the assignment. + super.field = 0; + } +} + +main() { + Super s = new Subclass()..test(); + // Test that the covariance check is performed. + Expect.throws(() => s.field = ''); +} diff --git a/tests/language/mixin_legacy/forwarding_stub_tearoff_test.dart b/tests/language/mixin_legacy/forwarding_stub_tearoff_test.dart new file mode 100644 index 00000000000..ad78a4d13e7 --- /dev/null +++ b/tests/language/mixin_legacy/forwarding_stub_tearoff_test.dart @@ -0,0 +1,38 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test for tearing off a method for which a forwarding super stub has been +// inserted. + +import 'package:expect/expect.dart'; + +class Super { + void method(T t) {} +} + +class Mixin { + void method(int t) {} +} + +// A forwarding super stub is inserted: +// +// void method(/*generic-covariant-impl*/ int t) => super.method(t); +// +class Class = Super with Mixin; + +class Subclass extends Class { + void test() { + // Test that we can tear off the method. + void Function(int) f = super.method; + f(0); + } +} + +main() { + Super s = new Subclass()..test(); + // Test that the covariance check is performed. + Expect.throws(() => s.method('')); +} diff --git a/tests/language/mixin_legacy/generic_test.dart b/tests/language/mixin_legacy/generic_test.dart new file mode 100644 index 00000000000..8fd06a36ce6 --- /dev/null +++ b/tests/language/mixin_legacy/generic_test.dart @@ -0,0 +1,37 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + s() { + return T; + } +} + +class M { + m() { + return T; + } +} + +class N { + n() { + return T; + } +} + +class C extends S> with M>, N> {} + +main() { + var c = new C(); + Expect.isTrue(c is S>); + Expect.equals("Map", c.s().toString()); + Expect.isTrue(c is M>); + Expect.equals("List", c.m().toString()); + Expect.isTrue(c is N>); + Expect.equals("Set", c.n().toString()); +} diff --git a/tests/language/mixin_legacy/getter_regression_test.dart b/tests/language/mixin_legacy/getter_regression_test.dart new file mode 100644 index 00000000000..feedfbfe6ed --- /dev/null +++ b/tests/language/mixin_legacy/getter_regression_test.dart @@ -0,0 +1,32 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Regression test case for dart2js bug where the getter for y wasn't +// properly mixed in. + +import "package:expect/expect.dart"; + +class C { + int x = -1; + int get y => x; +} + +class E { + int z = 10; +} + +class D extends E with C { + int w = 42; +} + +main() { + var d = new D(); + d.x = 37; + Expect.equals(37, d.x); + Expect.equals(10, d.z); + Expect.equals(42, d.w); + Expect.equals(37, d.y); +} diff --git a/tests/language/mixin_legacy/illegal_constructor_runtime_test.dart b/tests/language/mixin_legacy/illegal_constructor_runtime_test.dart new file mode 100644 index 00000000000..688d1a4f53d --- /dev/null +++ b/tests/language/mixin_legacy/illegal_constructor_runtime_test.dart @@ -0,0 +1,31 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class M0 { + factory M0(a, b, c) => throw "uncalled"; + factory M0.named() => throw "uncalled"; +} + +class M1 { + M1(); +} + +class M2 { + M2.named(); +} + +class C0 = Object with M0; + +class D0 extends Object with M0 {} + +main() { + new C0(); + + new D0(); +} diff --git a/tests/language/mixin_legacy/illegal_constructor_test.dart b/tests/language/mixin_legacy/illegal_constructor_test.dart new file mode 100644 index 00000000000..6c870ef1e4e --- /dev/null +++ b/tests/language/mixin_legacy/illegal_constructor_test.dart @@ -0,0 +1,120 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class M0 { + factory M0(a, b, c) => throw "uncalled"; + factory M0.named() => throw "uncalled"; +} + +class M1 { + M1(); +} + +class M2 { + M2.named(); +} + +class C0 = Object with M0; +class C1 = Object with M1; +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class C2 = Object with M2; +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class C3 = Object with M0, M1; +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class C4 = Object with M1, M0; +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class C5 = Object with M0, M2; +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class C6 = Object with M2, M0; +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR + +class D0 extends Object with M0 {} + +class D1 extends Object with M1 {} +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class D2 extends Object with M2 {} +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class D3 extends Object with M0, M1 {} +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class D4 extends Object with M1, M0 {} +// ^ +// [cfe] Can't use 'M1' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class D5 extends Object with M0, M2 {} +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +class D6 extends Object with M2, M0 {} +// ^ +// [cfe] Can't use 'M2' as a mixin because it has constructors. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR + +main() { + new C0(); + new C1(); + new C2(); + new C3(); + new C4(); + new C5(); + new C6(); + + new D0(); + new D1(); + new D2(); + new D3(); + new D4(); + new D5(); + new D6(); + + new C0(1, 2, 3); + // ^ + // [cfe] Too many positional arguments: 0 allowed, but 3 found. + // ^ + // [analyzer] COMPILE_TIME_ERROR.EXTRA_POSITIONAL_ARGUMENTS + new C0.named(); + // ^^^^^ + // [analyzer] COMPILE_TIME_ERROR.NEW_WITH_UNDEFINED_CONSTRUCTOR + // [cfe] Couldn't find constructor 'C0.named'. + new D0(1, 2, 3); + // ^ + // [cfe] Too many positional arguments: 0 allowed, but 3 found. + // ^ + // [analyzer] COMPILE_TIME_ERROR.EXTRA_POSITIONAL_ARGUMENTS + new D0.named(); + // ^^^^^ + // [analyzer] COMPILE_TIME_ERROR.NEW_WITH_UNDEFINED_CONSTRUCTOR + // [cfe] Couldn't find constructor 'D0.named'. +} diff --git a/tests/language/mixin_legacy/illegal_cycles_test.dart b/tests/language/mixin_legacy/illegal_cycles_test.dart new file mode 100644 index 00000000000..2b16836c94f --- /dev/null +++ b/tests/language/mixin_legacy/illegal_cycles_test.dart @@ -0,0 +1,89 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class M {} + +class M0 extends Object with M0 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M0' is a supertype of itself. +// ^ +// [cfe] 'Object with M0' is a supertype of itself. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +class M1 = Object with M1; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M1' is a supertype of itself. + +class M2 = Object with M3; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M2' is a supertype of itself. +class M3 = Object with M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M3' is a supertype of itself. + +class M4 = Object with M5; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M4' is a supertype of itself. +class M5 = Object with M6; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M5' is a supertype of itself. +class M6 = Object with M4; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M6' is a supertype of itself. + +class M7 extends Object with M8 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M7' is a supertype of itself. +// ^ +// [cfe] 'Object with M8' is a supertype of itself. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +class M8 extends Object with M7 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M8' is a supertype of itself. +// ^ +// [cfe] 'Object with M7' is a supertype of itself. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT + +class M9 = Object with M91; +// ^ +// [cfe] 'M9' is a supertype of itself. +class M91 = Object with M92; +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M91' is a supertype of itself. +class M92 = Object with M91; +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.RECURSIVE_INTERFACE_INHERITANCE +// [cfe] 'M92' is a supertype of itself. + +main() { + new M0(); + + new M1(); + + new M2(); + new M3(); + + new M4(); + new M5(); + new M6(); + + new M7(); + new M8(); + + new M9(); +} diff --git a/tests/language/mixin_legacy/illegal_object_test.dart b/tests/language/mixin_legacy/illegal_object_test.dart new file mode 100644 index 00000000000..13c2b48a0d8 --- /dev/null +++ b/tests/language/mixin_legacy/illegal_object_test.dart @@ -0,0 +1,29 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Object has a non-trivial constructor and hence cannot be used as mixin. + +class S {} + +class C0 extends S +// ^ +// [cfe] Can't use 'Object' as a mixin because it has constructors. + with + Object +// ^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR +{} + +class C1 = S with Object; +// ^ +// [cfe] Can't use 'Object' as a mixin because it has constructors. +// ^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_CLASS_DECLARES_CONSTRUCTOR + +main() { + new C0(); + new C1(); +} diff --git a/tests/language/mixin_legacy/illegal_static_access_runtime_test.dart b/tests/language/mixin_legacy/illegal_static_access_runtime_test.dart new file mode 100644 index 00000000000..8f92f287e26 --- /dev/null +++ b/tests/language/mixin_legacy/illegal_static_access_runtime_test.dart @@ -0,0 +1,25 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + static foo() => 42; +} + +class M { + static bar() => 87; +} + +class C = S with M; + +main() { + Expect.equals(42, S.foo()); + Expect.equals(87, M.bar()); +} diff --git a/tests/language/mixin_legacy/illegal_static_access_test.dart b/tests/language/mixin_legacy/illegal_static_access_test.dart new file mode 100644 index 00000000000..fbdb239f9ef --- /dev/null +++ b/tests/language/mixin_legacy/illegal_static_access_test.dart @@ -0,0 +1,31 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + static foo() => 42; +} + +class M { + static bar() => 87; +} + +class C = S with M; + +main() { + Expect.equals(42, S.foo()); + Expect.equals(87, M.bar()); + + Expect.throwsNoSuchMethodError(() => C.foo()); + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_METHOD + // [cfe] Member not found: 'C.foo'. + Expect.throwsNoSuchMethodError(() => C.bar()); + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_METHOD + // [cfe] Member not found: 'C.bar'. +} diff --git a/tests/language/mixin_legacy/illegal_super_use_runtime_test.dart b/tests/language/mixin_legacy/illegal_super_use_runtime_test.dart new file mode 100644 index 00000000000..9af3bf39162 --- /dev/null +++ b/tests/language/mixin_legacy/illegal_super_use_runtime_test.dart @@ -0,0 +1,61 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M {} + +class P0 { + foo() { + void inner() {} + inner(); + + (() {})(); + + return 42; + } +} + +class P1 { + bar() { + return 87; + } + + // The test method is strategically placed here to try to force the + // P1 class and its bar method to be resolved before resolving the + // mixin applications. + test() { + new C(); + var d = new D(); + var e = new E(); + var f = new F(); + Expect.equals(42, d.foo()); + Expect.equals(87, e.bar()); + Expect.equals(99, f.baz()); + } +} + +class P2 { + baz() { + return 99; + } +} + +class C = Object with M; +class D = Object with P0; +class E = Object with M, P1; +class F = Object with P2, M; + +main() { + var p1 = new P1(); + var p2 = new P2(); + Expect.equals(87, p1.bar()); + p1.test(); + Expect.equals(99, p2.baz()); +} diff --git a/tests/language/mixin_legacy/illegal_super_use_test.dart b/tests/language/mixin_legacy/illegal_super_use_test.dart new file mode 100644 index 00000000000..97c5992d57f --- /dev/null +++ b/tests/language/mixin_legacy/illegal_super_use_test.dart @@ -0,0 +1,91 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M {} + +class P0 { + foo() { + super.toString(); + super.foo(); + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no method named 'foo'. + super.bar = 100; + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no setter named 'bar'. + + void inner() { + super.toString(); + super.foo(); + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no method named 'foo'. + super.bar = 100; + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no setter named 'bar'. + } + + inner(); + + (() { + super.toString(); + super.foo(); + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no method named 'foo'. + super.bar = 100; + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.UNDEFINED_SUPER_MEMBER + // [cfe] Superclass has no setter named 'bar'. + })(); + + return 42; + } +} + +class P1 { + bar() { + super.toString(); + return 87; + } + + // The test method is strategically placed here to try to force the + // P1 class and its bar method to be resolved before resolving the + // mixin applications. + test() { + new C(); + var d = new D(); + var e = new E(); + var f = new F(); + Expect.equals(42, d.foo()); + Expect.equals(87, e.bar()); + Expect.equals(99, f.baz()); + } +} + +class P2 { + baz() { + super.toString(); + return 99; + } +} + +class C = Object with M; +class D = Object with P0; +class E = Object with M, P1; +class F = Object with P2, M; + +main() { + var p1 = new P1(); + var p2 = new P2(); + Expect.equals(87, p1.bar()); + p1.test(); + Expect.equals(99, p2.baz()); +} diff --git a/tests/language/mixin_legacy/illegal_superclass_runtime_test.dart b/tests/language/mixin_legacy/illegal_superclass_runtime_test.dart new file mode 100644 index 00000000000..11b0bceefdd --- /dev/null +++ b/tests/language/mixin_legacy/illegal_superclass_runtime_test.dart @@ -0,0 +1,85 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S1 extends Object {} + +class S2 extends S0 {} + +class M0 {} + +class M1 extends Object {} + +class M2 extends M0 {} + +class C00 = S0 with M0; +class C01 = S0 with M1; + +class C03 = S0 with M0, M1; + +class C10 = S1 with M0; +class C11 = S1 with M1; + +class C13 = S1 with M0, M1; + +class C20 = S2 with M0; +class C21 = S2 with M1; + +class C23 = S2 with M0, M1; + +class D00 extends S0 with M0 {} + +class D01 extends S0 with M1 {} + +class D03 extends S0 with M0, M1 {} + +class D10 extends S1 with M0 {} + +class D11 extends S1 with M1 {} + +class D13 extends S1 with M0, M1 {} + +class D20 extends S2 with M0 {} + +class D21 extends S2 with M1 {} + +class D23 extends S2 with M0, M1 {} + +main() { + new C00(); + new C01(); + + new C03(); + + new C10(); + new C11(); + + new C13(); + + new C20(); + new C21(); + + new C23(); + + new D00(); + new D01(); + + new D03(); + + new D10(); + new D11(); + + new D13(); + + new D20(); + new D21(); + + new D23(); +} diff --git a/tests/language/mixin_legacy/illegal_superclass_test.dart b/tests/language/mixin_legacy/illegal_superclass_test.dart new file mode 100644 index 00000000000..a23e53a288b --- /dev/null +++ b/tests/language/mixin_legacy/illegal_superclass_test.dart @@ -0,0 +1,256 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S1 extends Object {} + +class S2 extends S0 {} + +class M0 {} + +class M1 extends Object {} + +class M2 extends M0 {} + +class C00 = S0 with M0; +class C01 = S0 with M1; +class C02 = S0 with M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C03 = S0 with M0, M1; +class C04 = S0 with M0, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C05 = S0 with M2, M0; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C06 = S0 with M1, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C07 = S0 with M2, M1; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +class C10 = S1 with M0; +class C11 = S1 with M1; +class C12 = S1 with M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C13 = S1 with M0, M1; +class C14 = S1 with M0, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C15 = S1 with M2, M0; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C16 = S1 with M1, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C17 = S1 with M2, M1; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +class C20 = S2 with M0; +class C21 = S2 with M1; +class C22 = S2 with M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C23 = S2 with M0, M1; +class C24 = S2 with M0, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C25 = S2 with M2, M0; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C26 = S2 with M1, M2; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 25, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class C27 = S2 with M2, M1; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 21, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +class D00 extends S0 with M0 {} + +class D01 extends S0 with M1 {} + +class D02 extends S0 with M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D03 extends S0 with M0, M1 {} + +class D04 extends S0 with M0, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D05 extends S0 with M2, M0 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D06 extends S0 with M1, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D07 extends S0 with M2, M1 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +class D10 extends S1 with M0 {} + +class D11 extends S1 with M1 {} + +class D12 extends S1 with M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D13 extends S1 with M0, M1 {} + +class D14 extends S1 with M0, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D15 extends S1 with M2, M0 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D16 extends S1 with M1, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D17 extends S1 with M2, M1 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +class D20 extends S2 with M0 {} + +class D21 extends S2 with M1 {} + +class D22 extends S2 with M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D23 extends S2 with M0, M1 {} + +class D24 extends S2 with M0, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D25 extends S2 with M2, M0 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D26 extends S2 with M1, M2 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 31, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. +class D27 extends S2 with M2, M1 {} +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_INHERITS_FROM_NOT_OBJECT +// [error column 27, length 0] +// [cfe] The class 'M2' can't be used as a mixin because it extends a class other than 'Object'. + +main() { + new C00(); + new C01(); + new C02(); + new C03(); + new C04(); + new C05(); + new C06(); + new C07(); + + new C10(); + new C11(); + new C12(); + new C13(); + new C14(); + new C15(); + new C16(); + new C17(); + + new C20(); + new C21(); + new C22(); + new C23(); + new C24(); + new C25(); + new C26(); + new C27(); + + new D00(); + new D01(); + new D02(); + new D03(); + new D04(); + new D05(); + new D06(); + new D07(); + + new D10(); + new D11(); + new D12(); + new D13(); + new D14(); + new D15(); + new D16(); + new D17(); + + new D20(); + new D21(); + new D22(); + new D23(); + new D24(); + new D25(); + new D26(); + new D27(); +} diff --git a/tests/language/mixin_legacy/illegal_syntax_test.dart b/tests/language/mixin_legacy/illegal_syntax_test.dart new file mode 100644 index 00000000000..80765a77e43 --- /dev/null +++ b/tests/language/mixin_legacy/illegal_syntax_test.dart @@ -0,0 +1,61 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S { } +class G { } +class M { } + +class T0 = S with M; +abstract class T0A = S with M; +class T1 = final S with M; // //# 01: syntax error +class T2 = var S with M; // //# 02: syntax error +class T3 = const S with M; // //# 03: syntax error +class T4 = static S with M; // //# 04: syntax error +class T5 = external S with M; // //# 05: syntax error +class T6 = G with M; +class T7 = G> with M; + +class C0 extends abstract S with M { } // //# 06: syntax error +class C1 extends final S with M { } // //# 07: syntax error +class C2 extends var S with M { } // //# 08: syntax error +class C3 extends const S with M { } // //# 09: syntax error +class C4 extends static S with M { } // //# 10: syntax error +class C5 extends external S with M { } // //# 11: syntax error +class C6 extends G with M { } +class C7 extends G> with M { } + +class D0 extends S with M + implements M // //# 12: syntax error + implements M { } + +class D1 extends T0 { } + +class X = S; // //# 14: syntax error + +main() { + new T0(); + new T0A(); // //# 13: compile-time error + new T1(); // //# 01: continued + new T2(); // //# 02: continued + new T3(); // //# 03: continued + new T4(); // //# 04: continued + new T5(); // //# 05: continued + new T6(); + new T7(); + + new C0(); // //# 06: continued + new C1(); // //# 07: continued + new C2(); // //# 08: continued + new C3(); // //# 09: continued + new C4(); // //# 10: continued + new C5(); // //# 11: continued + new C6(); + new C7(); + + new D0(); // //# 12: continued + new D1(); + new X(); // //# 14: continued +} diff --git a/tests/language/mixin_legacy/implements2_test.dart b/tests/language/mixin_legacy/implements2_test.dart new file mode 100644 index 00000000000..0371416198c --- /dev/null +++ b/tests/language/mixin_legacy/implements2_test.dart @@ -0,0 +1,19 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Regression test for named mixin applications with implements clause. + +class A {} + +class S {} + +class M {} + +class C = S with M implements A; + +void main() { + new C(); +} diff --git a/tests/language/mixin_legacy/implements_test.dart b/tests/language/mixin_legacy/implements_test.dart new file mode 100644 index 00000000000..30a129d4e64 --- /dev/null +++ b/tests/language/mixin_legacy/implements_test.dart @@ -0,0 +1,79 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class I0 { + foo(); +} + +abstract class I1 { + bar(); +} + +abstract class I2 implements I0, I1 {} + +class M { + foo() => 42; + bar() => 87; +} + +class C0 = Object with M; +class C1 = Object with M implements I0; +class C2 = Object with M implements I1; +class C3 = Object with M implements I0, I1; +class C4 = Object with M implements I1, I0; +class C5 = Object with M implements I2; + +main() { + var c0 = new C0(); + Expect.equals(42, c0.foo()); + Expect.equals(87, c0.bar()); + Expect.isTrue(c0 is M); + Expect.isFalse(c0 is I0); + Expect.isFalse(c0 is I1); + Expect.isFalse(c0 is I2); + + var c1 = new C1(); + Expect.equals(42, c1.foo()); + Expect.equals(87, c1.bar()); + Expect.isTrue(c1 is M); + Expect.isTrue(c1 is I0); + Expect.isFalse(c1 is I1); + Expect.isFalse(c1 is I2); + + var c2 = new C2(); + Expect.equals(42, c2.foo()); + Expect.equals(87, c2.bar()); + Expect.isTrue(c2 is M); + Expect.isFalse(c2 is I0); + Expect.isTrue(c2 is I1); + Expect.isFalse(c1 is I2); + + var c3 = new C3(); + Expect.equals(42, c3.foo()); + Expect.equals(87, c3.bar()); + Expect.isTrue(c3 is M); + Expect.isTrue(c3 is I0); + Expect.isTrue(c3 is I1); + Expect.isFalse(c1 is I2); + + var c4 = new C4(); + Expect.equals(42, c4.foo()); + Expect.equals(87, c4.bar()); + Expect.isTrue(c4 is M); + Expect.isTrue(c4 is I0); + Expect.isTrue(c4 is I1); + Expect.isFalse(c1 is I2); + + var c5 = new C5(); + Expect.equals(42, c5.foo()); + Expect.equals(87, c5.bar()); + Expect.isTrue(c5 is M); + Expect.isTrue(c5 is I0); + Expect.isTrue(c5 is I1); + Expect.isTrue(c5 is I2); +} diff --git a/tests/language/mixin_legacy/implicit_covariance_test.dart b/tests/language/mixin_legacy/implicit_covariance_test.dart new file mode 100644 index 00000000000..51dec4795cf --- /dev/null +++ b/tests/language/mixin_legacy/implicit_covariance_test.dart @@ -0,0 +1,34 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'package:expect/expect.dart'; + +abstract class A { + foo(T x); +} + +abstract class B implements A {} + +class C { + foo(num x) { + if (x is! num) { + throw "Soundness issue: expected x to be num, got ${x.runtimeType}."; + } + } +} + +class D extends C with B {} + +class E = C with B; + +test(B b) { + b.foo("bar"); +} + +main() { + Expect.throws(() => test(new D())); + Expect.throws(() => test(new E())); +} diff --git a/tests/language/mixin_legacy/inference_mixin_field_test.dart b/tests/language/mixin_legacy/inference_mixin_field_test.dart new file mode 100644 index 00000000000..7571e8acb8a --- /dev/null +++ b/tests/language/mixin_legacy/inference_mixin_field_test.dart @@ -0,0 +1,30 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Mixin { + var field; + createIt() { + if (field == null) field = 42; + } +} + +class A { + A(foo); +} + +class B extends A with Mixin { + // Because [super] references a synthesized constructor, dart2js + // used to not see the null assignment to it. + B(foo) : super(foo); +} + +main() { + var a = new B(42); + a.createIt(); + Expect.equals(42, a.field); +} diff --git a/tests/language/mixin_legacy/interface_check_runtime_test.dart b/tests/language/mixin_legacy/interface_check_runtime_test.dart new file mode 100644 index 00000000000..4d4a19a1808 --- /dev/null +++ b/tests/language/mixin_legacy/interface_check_runtime_test.dart @@ -0,0 +1,33 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class Thing {} + +class SubThing extends Thing { + void sub() {} +} + +class A { + Thing get thing => new Thing(); +} + +abstract class B implements A { + @override + SubThing get thing; +} + +class C extends A // + +{} + +main() { + new C().thing // + + ; +} diff --git a/tests/language/mixin_legacy/interface_check_test.dart b/tests/language/mixin_legacy/interface_check_test.dart new file mode 100644 index 00000000000..16ab862fe98 --- /dev/null +++ b/tests/language/mixin_legacy/interface_check_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class Thing {} + +class SubThing extends Thing { + void sub() {} +} + +class A { + Thing get thing => new Thing(); +} + +abstract class B implements A { + @override + SubThing get thing; +} + +class C extends A // +// ^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_IMPLEMENTATION_OVERRIDE +// [cfe] The implementation of 'thing' in the non-abstract class 'C' does not conform to its interface. + with + B {} + +main() { + new C() + .thing // + .sub(); +} diff --git a/tests/language/mixin_legacy/invalid_bound2_test.dart b/tests/language/mixin_legacy/invalid_bound2_test.dart new file mode 100644 index 00000000000..62f978f3b97 --- /dev/null +++ b/tests/language/mixin_legacy/invalid_bound2_test.dart @@ -0,0 +1,50 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S extends S0 {} + +class M {} + +class A extends S with M {} + +// A StaticWarning is reported here and in C, D, and E below, because U and V +// are not bounded. The purpose of this test is to verify bound checking in S, +// M, and A, the reason no bounds are declared for U and V here. +class B extends S with M {} //# 04: continued +class B extends S with M {} //# 05: continued +class B extends S with M {} //# 06: continued + +class C extends S with M {} //# 07: continued +class C extends S with M {} //# 08: continued +class C extends S with M {} //# 09: continued + +class D extends S with M {} //# 10: continued +class D extends S with M {} //# 11: continued +class D extends S with M {} //# 12: continued + +class E extends S with M {} //# 13: continued +class E extends S with M {} //# 14: continued +class E extends S with M {} //# 15: continued + +main() { + new A(); // //# 01: ok + new A(); // //# 02: compile-time error + new A(); // //# 03: compile-time error + new B(); // //# 04: compile-time error + new B(); // //# 05: compile-time error + new B(); // //# 06: compile-time error + new C(); // //# 07: compile-time error + new C(); // //# 08: compile-time error + new C(); // //# 09: compile-time error + new D(); // //# 10: compile-time error + new D(); // //# 11: compile-time error + new D(); // //# 12: compile-time error + new E(); // //# 13: compile-time error + new E(); // //# 14: compile-time error + new E(); // //# 15: compile-time error +} diff --git a/tests/language/mixin_legacy/invalid_bound_test.dart b/tests/language/mixin_legacy/invalid_bound_test.dart new file mode 100644 index 00000000000..daac54d40b3 --- /dev/null +++ b/tests/language/mixin_legacy/invalid_bound_test.dart @@ -0,0 +1,41 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S extends S0 {} + +class M {} + +class A extends S with M {} + +// A CompileTimeError is reported here and in C, D, and E below, because T is +// not bounded. The purpose of this test is to verify bound checking in S, M, +// and A, the reason no bound is declared for T here. +class B extends S with M {} //# 03: continued +class B extends S with M {} //# 04: continued + +class C extends S with M {} //# 05: continued +class C extends S with M {} //# 06: continued + +class D extends S with M {} //# 07: continued +class D extends S with M {} //# 08: continued + +class E extends S with M {} //# 09: continued +class E extends S with M {} //# 10: continued + +main() { + new A(); // //# 01: ok + new A(); // //# 02: compile-time error + new B(); // //# 03: compile-time error + new B(); // //# 04: compile-time error + new C(); // //# 05: compile-time error + new C(); // //# 06: compile-time error + new D(); // //# 07: compile-time error + new D(); // //# 08: compile-time error + new E(); // //# 09: compile-time error + new E(); // //# 10: compile-time error +} diff --git a/tests/language/mixin_legacy/invalid_inheritance1_test.dart b/tests/language/mixin_legacy/invalid_inheritance1_test.dart new file mode 100644 index 00000000000..4bb6d90d4b4 --- /dev/null +++ b/tests/language/mixin_legacy/invalid_inheritance1_test.dart @@ -0,0 +1,13 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class C extends Object + with Malformed // //# 01: compile-time error + with T // //# 02: compile-time error + with T // //# 03: compile-time error +{} + +main() => new C(); diff --git a/tests/language/mixin_legacy/invalid_inheritance2_test.dart b/tests/language/mixin_legacy/invalid_inheritance2_test.dart new file mode 100644 index 00000000000..ed27a453aad --- /dev/null +++ b/tests/language/mixin_legacy/invalid_inheritance2_test.dart @@ -0,0 +1,13 @@ +// Copyright (c) 2023, 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 C = Object with Malformed; // //# 01: compile-time error +class C = Object with T; // //# 02: compile-time error +class C = OBject with T; // //# 03: compile-time error + +main() { + new C(); // //# 01: continued + new C(); // //# 02: continued + new C(); // //# 03: continued +} diff --git a/tests/language/mixin_legacy/invalid_override_in_mixin_runtime_test.dart b/tests/language/mixin_legacy/invalid_override_in_mixin_runtime_test.dart new file mode 100644 index 00000000000..426342817b5 --- /dev/null +++ b/tests/language/mixin_legacy/invalid_override_in_mixin_runtime_test.dart @@ -0,0 +1,25 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'package:expect/expect.dart'; + +class A {} + +class C extends Object with A { + test() { + print("Hello from test"); + } +} + +main() { + C c = new C(); + c.test(); + dynamic cc = c; + Expect.throwsNoSuchMethodError(() => cc.doesntExist()); +} diff --git a/tests/language/mixin_legacy/invalid_override_in_mixin_test.dart b/tests/language/mixin_legacy/invalid_override_in_mixin_test.dart new file mode 100644 index 00000000000..a85159bb969 --- /dev/null +++ b/tests/language/mixin_legacy/invalid_override_in_mixin_test.dart @@ -0,0 +1,31 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'package:expect/expect.dart'; + +class A { + noSuchMethod() {} +//^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +// [cfe] The method 'A.noSuchMethod' has fewer positional arguments than those of overridden method 'Object.noSuchMethod'. +} + +class C extends Object with A { +// ^ +// [cfe] Applying the mixin 'A' to 'Object' introduces an erroneous override of 'noSuchMethod'. +// ^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + test() { + print("Hello from test"); + } +} + +main() { + C c = new C(); + c.test(); + dynamic cc = c; + Expect.throwsNoSuchMethodError(() => cc.doesntExist()); +} diff --git a/tests/language/mixin_legacy/is_test.dart b/tests/language/mixin_legacy/is_test.dart new file mode 100644 index 00000000000..340c007e575 --- /dev/null +++ b/tests/language/mixin_legacy/is_test.dart @@ -0,0 +1,85 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S {} + +class M1 {} + +class M2 {} + +class C = S with M1; +class D = S with M1, M2; +class E = S with M2, M1; + +class F extends E {} + +class C_ = S with M1; +class D_ = S with M1, M2; +class E_ = S with M2, M1; + +class F_ extends E_ {} + +main() { + var c = new C(); + Expect.isTrue(c is C); + Expect.isFalse(c is D); + Expect.isFalse(c is E); + Expect.isFalse(c is F); + Expect.isTrue(c is S); + Expect.isTrue(c is M1); + Expect.isFalse(c is M2); + + var d = new D(); + Expect.isFalse(d is C); + Expect.isTrue(d is D); + Expect.isFalse(d is E); + Expect.isFalse(d is F); + Expect.isTrue(d is S); + Expect.isTrue(d is M1); + Expect.isTrue(d is M2); + + var e = new E(); + Expect.isFalse(e is C); + Expect.isFalse(e is D); + Expect.isTrue(e is E); + Expect.isFalse(e is F); + Expect.isTrue(e is S); + Expect.isTrue(e is M1); + Expect.isTrue(e is M2); + + var f = new F(); + Expect.isFalse(f is C); + Expect.isFalse(f is D); + Expect.isTrue(f is E); + Expect.isTrue(f is F); + Expect.isTrue(f is S); + Expect.isTrue(f is M1); + Expect.isTrue(f is M2); + + // Make sure we get a new class for each mixin + // application (at least the named ones). + Expect.isFalse(c is C_); + Expect.isFalse(c is D_); + Expect.isFalse(c is E_); + Expect.isFalse(c is F_); + + Expect.isFalse(d is C_); + Expect.isFalse(d is D_); + Expect.isFalse(d is E_); + Expect.isFalse(d is F_); + + Expect.isFalse(e is C_); + Expect.isFalse(e is D_); + Expect.isFalse(e is E_); + Expect.isFalse(e is F_); + + Expect.isFalse(f is C_); + Expect.isFalse(f is D_); + Expect.isFalse(f is E_); + Expect.isFalse(f is F_); +} diff --git a/tests/language/mixin_legacy/issue10216_2_test.dart b/tests/language/mixin_legacy/issue10216_2_test.dart new file mode 100644 index 00000000000..46f8eaca174 --- /dev/null +++ b/tests/language/mixin_legacy/issue10216_2_test.dart @@ -0,0 +1,22 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M1 = Object with M0; +class M2 = Object with M1; + +class M0 { + foo() => 42; +} + +makeM2() { + return [new Object(), new M2()].last as M2; +} + +main() { + Expect.equals(42, makeM2().foo()); +} diff --git a/tests/language/mixin_legacy/issue10216_test.dart b/tests/language/mixin_legacy/issue10216_test.dart new file mode 100644 index 00000000000..e49f23bdd75 --- /dev/null +++ b/tests/language/mixin_legacy/issue10216_test.dart @@ -0,0 +1,35 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class A { + foo(x, [y]) => '$x;$y'; +} + +class B extends A with M1, M2, M3 {} + +class M1 {} + +class M2 { + plain(x) => 'P $x'; + bar(x, [y]) => '$y,$x'; +} + +class M3 {} + +makeB() { + return [new A(), new B()].last as B; +} + +main() { + var b = makeB(); + Expect.equals('1;2', b.foo(1, 2)); + Expect.equals('2;null', b.foo(2)); + Expect.equals('P 3', b.plain(3)); + Expect.equals('100,4', b.bar(4, 100)); + Expect.equals('null,5', b.bar(5)); +} diff --git a/tests/language/mixin_legacy/lib_extends_field_lib.dart b/tests/language/mixin_legacy/lib_extends_field_lib.dart new file mode 100644 index 00000000000..5edfac75db0 --- /dev/null +++ b/tests/language/mixin_legacy/lib_extends_field_lib.dart @@ -0,0 +1,17 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +library mixin_lib_extends_field_lib; + +mixin M1 { + final bar = "M1-bar"; +} + +mixin M2 { + var baz = "M2-$_baz"; +} + +var _baz = "baz"; diff --git a/tests/language/mixin_legacy/lib_extends_field_test.dart b/tests/language/mixin_legacy/lib_extends_field_test.dart new file mode 100644 index 00000000000..2e2117ef091 --- /dev/null +++ b/tests/language/mixin_legacy/lib_extends_field_test.dart @@ -0,0 +1,119 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +library mixin_lib_extends_field_test; + +import 'package:expect/expect.dart'; +import "lib_extends_field_lib.dart" as L; + +class S { + var foo = "S-foo"; +} + +class C extends S with L.M1 {} + +class D extends S with L.M1, L.M2 {} + +class E extends S with L.M2, L.M1 {} + +class F extends E { + var fez = "F-fez"; +} + +main() { + dynamic c = new C(); + dynamic d = new D(); + dynamic e = new E(); + dynamic f = new F(); + + Expect.equals("S-foo", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez", f.fez); + + c.foo = "S-foo-c"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + d.foo = "S-foo-d"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo", e.foo); + Expect.equals("S-foo", f.foo); + + e.foo = "S-foo-e"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo", f.foo); + + f.foo = "S-foo-f"; + Expect.equals("S-foo-c", c.foo); + Expect.equals("S-foo-d", d.foo); + Expect.equals("S-foo-e", e.foo); + Expect.equals("S-foo-f", f.foo); + + Expect.throwsNoSuchMethodError(() => c.bar = 0); + Expect.throwsNoSuchMethodError(() => d.bar = 0); + Expect.throwsNoSuchMethodError(() => e.bar = 0); + Expect.throwsNoSuchMethodError(() => f.bar = 0); + Expect.equals("M1-bar", c.bar); + Expect.equals("M1-bar", d.bar); + Expect.equals("M1-bar", e.bar); + Expect.equals("M1-bar", f.bar); + + Expect.throwsNoSuchMethodError(() => c.baz = 0); + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + + d.baz = "M2-baz-d"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz", e.baz); + Expect.equals("M2-baz", f.baz); + Expect.equals("M2-baz", f.baz); + + e.baz = "M2-baz-e"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz", f.baz); + + f.baz = "M2-baz-f"; + Expect.throwsNoSuchMethodError(() => c.baz); + Expect.equals("M2-baz-d", d.baz); + Expect.equals("M2-baz-e", e.baz); + Expect.equals("M2-baz-f", f.baz); + + Expect.throwsNoSuchMethodError(() => c.fez = 0); + Expect.throwsNoSuchMethodError(() => d.fez = 0); + Expect.throwsNoSuchMethodError(() => e.fez = 0); + + f.fez = "F-fez-f"; + Expect.throwsNoSuchMethodError(() => c.fez); + Expect.throwsNoSuchMethodError(() => d.fez); + Expect.throwsNoSuchMethodError(() => e.fez); + Expect.equals("F-fez-f", f.fez); +} diff --git a/tests/language/mixin_legacy/lib_extends_method_lib.dart b/tests/language/mixin_legacy/lib_extends_method_lib.dart new file mode 100644 index 00000000000..53793854950 --- /dev/null +++ b/tests/language/mixin_legacy/lib_extends_method_lib.dart @@ -0,0 +1,30 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +library mixin_lib_extends_method_lib; + +mixin M1 { + bar() => "M1-bar"; + + clo(s) { + var l = s; + return (s) => "$l$s"; + } +} + +mixin M2 { + // Make sure mixed-in method has access to library-private names. + bar() => _M2_bar(); + baz() => _M2_baz; + fez() => "M2-${_fez()}"; + _fez() => "fez"; +} + +_M2_bar() { + return "M2-bar"; +} + +var _M2_baz = "M2-baz"; diff --git a/tests/language/mixin_legacy/lib_extends_method_test.dart b/tests/language/mixin_legacy/lib_extends_method_test.dart new file mode 100644 index 00000000000..2ff698c3606 --- /dev/null +++ b/tests/language/mixin_legacy/lib_extends_method_test.dart @@ -0,0 +1,55 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +library mixin_lib_extends_method_test; + +import "package:expect/expect.dart"; +import "lib_extends_method_lib.dart" as L; + +class S { + foo() => "S-foo"; + baz() => "S-baz"; +} + +class C extends S with L.M1 {} + +class D extends S with L.M1, L.M2 {} + +class E extends S with L.M2, L.M1 {} + +class F extends E { + fez() => "F-fez"; +} + +main() { + dynamic c = new C(); + Expect.equals("S-foo", c.foo()); + Expect.equals("M1-bar", c.bar()); + Expect.equals("S-baz", c.baz()); + Expect.throwsNoSuchMethodError(() => c.fez()); + Expect.equals("sugus", c.clo("su")("gus")); + + var d = new D(); + Expect.equals("S-foo", d.foo()); + Expect.equals("M2-bar", d.bar()); + Expect.equals("M2-baz", d.baz()); + Expect.equals("M2-fez", d.fez()); + Expect.equals("sugus", d.clo("su")("gus")); + + var e = new E(); + Expect.equals("S-foo", e.foo()); + Expect.equals("M1-bar", e.bar()); + Expect.equals("M2-baz", e.baz()); + Expect.equals("M2-fez", e.fez()); + Expect.equals("sugus", e.clo("su")("gus")); + + var f = new F(); + Expect.equals("S-foo", f.foo()); + Expect.equals("M1-bar", f.bar()); + Expect.equals("M2-baz", f.baz()); + Expect.equals("F-fez", f.fez()); + Expect.equals("sugus", f.clo("su")("gus")); +} diff --git a/tests/language/mixin_legacy/method_override_runtime_test.dart b/tests/language/mixin_legacy/method_override_runtime_test.dart new file mode 100644 index 00000000000..f365d07dd6b --- /dev/null +++ b/tests/language/mixin_legacy/method_override_runtime_test.dart @@ -0,0 +1,150 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Signature conformance test. +abstract class CII { + int id(int x); +} + +class CSI { + String id(int x) => "$x"; +} + +class CIS { + int id(String x) => 0; +} + +class CTT { + T id(T x) => x; +} + +// Wrong return type. + +// Wrong argument type. + +// Similar as the above but using an instantiated class instead. +abstract class C5 = CII with CTT; + +abstract class C6 extends CII with CTT {} + +// Named parameters +abstract class NIIx { + int? id({int? x}) => x; +} + +class NIIxy { + int? id({int? x, int? y}) => y; +} + +class NIIy { + int? id({int? y}) => y; +} + +class NII { + int? id(int? x) => x; +} + +// It's OK to introduce more named parameters. +abstract class N1 = NIIx with NIIxy; + +abstract class N2 extends NIIx with NIIxy {} +// It's NOT OK to rename named parameters. + +// It's NOT OK to drop named parameters. + +class NBABxy { + B? id({A? x, B? y}) => y; +} + +class NTTy { + T? id({T? y}) => y; +} + +class NTTx { + T? id(T? x) => x; +} + +// Same as above but with generic classes. +abstract class N7 = NIIx with NBABxy; + +abstract class N8 extends NIIx with NBABxy {} + +// Optional positional parameters +abstract class OII { + int? id([int? x]) => x; +} + +class OIII { + int? id([int? x, int? y]) => y; +} + +class OIIy { + int? id([int? y]) => y; +} + +class PII { + int? id(int? x) => x; +} + +// It's OK to introduce more optional parameters. +abstract class O1 = OII with OIII; + +abstract class O2 extends OII with OIII {} + +// It's OK to rename optional parameters. +abstract class O3 = OII with OIIy; + +abstract class O4 extends OII with OIIy {} +// It's NOT OK to drop optional parameters. + +class OBAB { + B? id([A? x, B? y]) => y; +} + +class OTTy { + T? id([T? y]) => y; +} + +class PTT { + T? id(T? x) => x; +} + +// Same as above but with generic classes. +abstract class O7 = OII with OBAB; + +abstract class O8 extends OII with OBAB {} + +abstract class O11 = OII with OTTy; + +abstract class O12 extends OII with OTTy {} + +// More tests with generic classes. +abstract class GTTnum { + T id(x); +} + +class MTTnum { + T id(x) => x; +} + +class MTTint { + T id(x) => x; +} + +class MTT { + T id(x) => x; +} + +class MTTnumR { + T id(x) => x; +} + +class G1 = GTTnum with MTTnum; + +void main() {} diff --git a/tests/language/mixin_legacy/method_override_test.dart b/tests/language/mixin_legacy/method_override_test.dart new file mode 100644 index 00000000000..5ddf7720413 --- /dev/null +++ b/tests/language/mixin_legacy/method_override_test.dart @@ -0,0 +1,285 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Signature conformance test. +abstract class CII { + int id(int x); +} + +class CSI { + String id(int x) => "$x"; +} + +class CIS { + int id(String x) => 0; +} + +class CTT { + T id(T x) => x; +} + +// Wrong return type. +abstract class C1 = CII with CIS; +// ^ +// [cfe] The mixin application class 'C1' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class C2 extends CII with CIS {} +// ^ +// [cfe] Applying the mixin 'CIS' to 'CII' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// Wrong argument type. +abstract class C3 = CII with CSI; +// ^ +// [cfe] The mixin application class 'C3' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class C4 extends CII with CSI {} +// ^ +// [cfe] Applying the mixin 'CSI' to 'CII' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// Similar as the above but using an instantiated class instead. +abstract class C5 = CII with CTT; + +abstract class C6 extends CII with CTT {} + +abstract class C7 = CII with CTT; +// ^ +// [cfe] The mixin application class 'C7' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class C8 extends CII with CTT {} +// ^ +// [cfe] Applying the mixin 'CTT' to 'CII' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// Named parameters +abstract class NIIx { + int? id({int? x}) => x; +} + +class NIIxy { + int? id({int? x, int? y}) => y; +} + +class NIIy { + int? id({int? y}) => y; +} + +class NII { + int? id(int? x) => x; +} + +// It's OK to introduce more named parameters. +abstract class N1 = NIIx with NIIxy; + +abstract class N2 extends NIIx with NIIxy {} + +// It's NOT OK to rename named parameters. +abstract class N3 = NIIx with NIIy; +// ^ +// [cfe] The mixin application class 'N3' introduces an erroneous override of 'id'. +// ^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N4 extends NIIx with NIIy {} +// ^ +// [cfe] Applying the mixin 'NIIy' to 'NIIx' introduces an erroneous override of 'id'. +// ^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// It's NOT OK to drop named parameters. +abstract class N5 = NIIx with NII; +// ^ +// [cfe] The mixin application class 'N5' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N6 extends NIIx with NII {} +// ^ +// [cfe] Applying the mixin 'NII' to 'NIIx' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +class NBABxy { + B? id({A? x, B? y}) => y; +} + +class NTTy { + T? id({T? y}) => y; +} + +class NTTx { + T? id(T? x) => x; +} + +// Same as above but with generic classes. +abstract class N7 = NIIx with NBABxy; + +abstract class N8 extends NIIx with NBABxy {} + +abstract class N9 = NIIx with NBABxy; +// ^ +// [cfe] The mixin application class 'N9' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N10 extends NIIx with NBABxy {} +// ^ +// [cfe] Applying the mixin 'NBABxy' to 'NIIx' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N11 = NIIx with NTTy; +// ^ +// [cfe] The mixin application class 'N11' introduces an erroneous override of 'id'. +// ^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N12 extends NIIx with NTTy {} +// ^ +// [cfe] Applying the mixin 'NTTy' to 'NIIx' introduces an erroneous override of 'id'. +// ^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N13 = NIIx with NTTx; +// ^ +// [cfe] The mixin application class 'N13' introduces an erroneous override of 'id'. +// ^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class N14 extends NIIx with NTTx {} +// ^ +// [cfe] Applying the mixin 'NTTx' to 'NIIx' introduces an erroneous override of 'id'. +// ^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// Optional positional parameters +abstract class OII { + int? id([int? x]) => x; +} + +class OIII { + int? id([int? x, int? y]) => y; +} + +class OIIy { + int? id([int? y]) => y; +} + +class PII { + int? id(int? x) => x; +} + +// It's OK to introduce more optional parameters. +abstract class O1 = OII with OIII; + +abstract class O2 extends OII with OIII {} + +// It's OK to rename optional parameters. +abstract class O3 = OII with OIIy; + +abstract class O4 extends OII with OIIy {} + +// It's NOT OK to drop optional parameters. +abstract class O5 = OII with PII; +// ^ +// [cfe] The mixin application class 'O5' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class O6 extends OII with PII {} +// ^ +// [cfe] Applying the mixin 'PII' to 'OII' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +class OBAB { + B? id([A? x, B? y]) => y; +} + +class OTTy { + T? id([T? y]) => y; +} + +class PTT { + T? id(T? x) => x; +} + +// Same as above but with generic classes. +abstract class O7 = OII with OBAB; + +abstract class O8 extends OII with OBAB {} + +abstract class O9 = OII with OBAB; +// ^ +// [cfe] The mixin application class 'O9' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class O10 extends OII with OBAB {} +// ^ +// [cfe] Applying the mixin 'OBAB' to 'OII' introduces an erroneous override of 'id'. +// ^^^^^^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class O11 = OII with OTTy; + +abstract class O12 extends OII with OTTy {} + +abstract class O13 = OII with PTT; +// ^ +// [cfe] The mixin application class 'O13' introduces an erroneous override of 'id'. +// ^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +abstract class O14 extends OII with PTT {} +// ^ +// [cfe] Applying the mixin 'PTT' to 'OII' introduces an erroneous override of 'id'. +// ^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +// More tests with generic classes. +abstract class GTTnum { + T id(x); +} + +class MTTnum { + T id(x) => x; +} + +class MTTint { + T id(x) => x; +} + +class MTT { + T id(x) => x; +} + +class MTTnumR { + T id(x) => x; +} + +class G1 = GTTnum with MTTnum; +class G2 = GTTnum with MTTint; +// ^ +// [cfe] The mixin application class 'G2' introduces an erroneous override of 'id'. +// ^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +class G3 = GTTnum with MTT; +// ^ +// [cfe] The mixin application class 'G3' introduces an erroneous override of 'id'. +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +class G4 = GTTnum with MTTnumR; +// ^ +// [cfe] The mixin application class 'G4' introduces an erroneous override of 'id'. +// ^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE +class G5 = GTTnum with CII; +// ^^ +// [analyzer] COMPILE_TIME_ERROR.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER +// [cfe] The mixin application class 'G5' introduces an erroneous override of 'id'. +// ^ +// [cfe] The non-abstract class 'G5' is missing implementations for these members: +// ^^^ +// [analyzer] COMPILE_TIME_ERROR.INVALID_OVERRIDE + +void main() {} diff --git a/tests/language/mixin_legacy/method_test.dart b/tests/language/mixin_legacy/method_test.dart new file mode 100644 index 00000000000..063d4818cee --- /dev/null +++ b/tests/language/mixin_legacy/method_test.dart @@ -0,0 +1,56 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + foo() => "S-foo"; + baz() => "S-baz"; +} + +class M1 { + bar() => "M1-bar"; +} + +class M2 { + bar() => "M2-bar"; + baz() => "M2-baz"; + fez() => "M2-fez"; +} + +class C = S with M1; +class D = S with M1, M2; +class E = S with M2, M1; + +class F extends E { + fez() => "F-fez"; +} + +main() { + dynamic c = new C(); + Expect.equals("S-foo", c.foo()); + Expect.equals("M1-bar", c.bar()); + Expect.equals("S-baz", c.baz()); + Expect.throwsNoSuchMethodError(() => c.fez()); + + var d = new D(); + Expect.equals("S-foo", d.foo()); + Expect.equals("M2-bar", d.bar()); + Expect.equals("M2-baz", d.baz()); + Expect.equals("M2-fez", d.fez()); + + var e = new E(); + Expect.equals("S-foo", e.foo()); + Expect.equals("M1-bar", e.bar()); + Expect.equals("M2-baz", e.baz()); + Expect.equals("M2-fez", e.fez()); + + var f = new F(); + Expect.equals("S-foo", f.foo()); + Expect.equals("M1-bar", f.bar()); + Expect.equals("M2-baz", f.baz()); + Expect.equals("F-fez", f.fez()); +} diff --git a/tests/language/mixin_legacy/mixin2_test.dart b/tests/language/mixin_legacy/mixin2_test.dart new file mode 100644 index 00000000000..c59998783f3 --- /dev/null +++ b/tests/language/mixin_legacy/mixin2_test.dart @@ -0,0 +1,36 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M { + t() { + return T; + } +} + +class A = Object with M; + +class B = Object with A; + +class C = Object with M>; + +class D = Object with C>; + +class E extends A {} + +class F extends B {} + +class G extends C {} + +class H extends D> {} + +main() { + Expect.equals("num", new E().t().toString()); + Expect.equals("String", new F().t().toString()); + Expect.equals("List", new G().t().toString()); + Expect.equals("List>>", new H().t().toString()); +} diff --git a/tests/language/mixin_legacy/mixin3_test.dart b/tests/language/mixin_legacy/mixin3_test.dart new file mode 100644 index 00000000000..55934802f85 --- /dev/null +++ b/tests/language/mixin_legacy/mixin3_test.dart @@ -0,0 +1,53 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M { + t() { + return T; + } +} + +class A = Object with M>; + +class B0 = Object with A>; + +class B1 = Object with A>; + +class C0 extends B0 {} + +class C1 extends B1 {} + +class A2 = Object with M>; + +class B2 = Object with A2, List>; + +class B3 = Object with A2, List>; + +class C2 extends B2 {} + +class C3 extends B3 {} + +class N { + q() { + return 42; + } +} + +class O = Object with N; + +class P = Object with O; + +class Q extends P {} + +main() { + Expect.equals("List>", new C0().t().toString()); + Expect.equals("List>", new C1().t().toString()); + Expect.equals("Map, List>", new C2().t().toString()); + Expect.equals("Map, List>", new C3().t().toString()); + Expect.equals(42, new Q().q()); +} diff --git a/tests/language/mixin_legacy/mixin4_test.dart b/tests/language/mixin_legacy/mixin4_test.dart new file mode 100644 index 00000000000..aa3457b6ba9 --- /dev/null +++ b/tests/language/mixin_legacy/mixin4_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class S {} + +class M { + t() { + return T; + } +} + +class A = Object with M> implements I; + +class C = S with A> implements J; + +main() { + var c = new C(); + Expect.equals("Map>", c.t().toString()); + Expect.isTrue(c is I>); + Expect.isTrue(c is J); + Expect.isTrue(c is S); + Expect.isTrue(c is A>); + Expect.isTrue(c is M>>); +} diff --git a/tests/language/mixin_legacy/mixin5_test.dart b/tests/language/mixin_legacy/mixin5_test.dart new file mode 100644 index 00000000000..b00af7fff73 --- /dev/null +++ b/tests/language/mixin_legacy/mixin5_test.dart @@ -0,0 +1,38 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class K {} + +class S {} + +class M { + m() { + return T; + } +} + +class A = Object with M> implements I; + +class B = Object with A> implements J; + +class C = S> with B> implements K; + +main() { + var c = new C(); + Expect.equals("Map, Set>>", c.m().toString()); + Expect.isTrue(c is K); + Expect.isTrue(c is J>); + Expect.isTrue(c is I>>); + Expect.isTrue(c is S>); + Expect.isTrue(c is A, Set>>); + Expect.isTrue(c is M, Set>>>); +} diff --git a/tests/language/mixin_legacy/mixin6_test.dart b/tests/language/mixin_legacy/mixin6_test.dart new file mode 100644 index 00000000000..90a1d6ffff3 --- /dev/null +++ b/tests/language/mixin_legacy/mixin6_test.dart @@ -0,0 +1,38 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class K {} + +class S {} + +class M { + m() { + return T; + } +} + +class A = Object with M> implements I; + +class B = Object with A> implements J; + +class C = S> with B implements K; // B is raw. + +main() { + var c = new C(); + Expect.equals("Map>", c.m().toString()); + Expect.isTrue(c is K); + Expect.isTrue(c is J); + Expect.isTrue(c is I); + Expect.isTrue(c is S>); + Expect.isTrue(c is A); + Expect.isTrue(c is M>); +} diff --git a/tests/language/mixin_legacy/mixin7_test.dart b/tests/language/mixin_legacy/mixin7_test.dart new file mode 100644 index 00000000000..603913a8d2a --- /dev/null +++ b/tests/language/mixin_legacy/mixin7_test.dart @@ -0,0 +1,38 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class K {} + +class S {} + +class M { + m() { + return T; + } +} + +class A = Object with M implements I; // M is raw. + +class B = Object with A implements J; // A is raw. + +class C = S> with B implements K; // B is raw. + +main() { + var c = new C(); + Expect.equals("dynamic", c.m().toString()); + Expect.isTrue(c is K); + Expect.isTrue(c is J); + Expect.isTrue(c is I); + Expect.isTrue(c is S>); + Expect.isTrue(c is A); + Expect.isTrue(c is M); +} diff --git a/tests/language/mixin_legacy/mixin_bound2_test.dart b/tests/language/mixin_legacy/mixin_bound2_test.dart new file mode 100644 index 00000000000..2a69bb84d8d --- /dev/null +++ b/tests/language/mixin_legacy/mixin_bound2_test.dart @@ -0,0 +1,39 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class K {} + +class S, V> {} + +class M> { + m() { + return T; + } +} + +class A> = Object with M> implements I; + +class B> = Object with A> implements J; + +class C = S, T> with B> implements K; + +main() { + var c = new C(); + Expect.equals("Map, Set>>", c.m().toString()); + Expect.isTrue(c is K); + Expect.isTrue(c is J>); + Expect.isTrue(c is I>>); + Expect.isTrue(c is S, int>); + Expect.isTrue(c is A, Set>>); + Expect.isTrue( + c is M, Set>, Map, Set>>>); +} diff --git a/tests/language/mixin_legacy/mixin_bound_test.dart b/tests/language/mixin_legacy/mixin_bound_test.dart new file mode 100644 index 00000000000..370e3509975 --- /dev/null +++ b/tests/language/mixin_legacy/mixin_bound_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class I {} + +class J {} + +class S, V> {} + +class M> { + t() { + return T; + } +} + +class A = Object with M> implements I; + +class C = S, T> with A> implements J; + +main() { + var c = new C(); + Expect.equals("Map>", c.t().toString()); + Expect.isTrue(c is I>); + Expect.isTrue(c is J); + Expect.isTrue(c is S, int>); + Expect.isTrue(c is A>); + Expect.isTrue(c is M, Map>>); +} diff --git a/tests/language/mixin_legacy/mixin_test.dart b/tests/language/mixin_legacy/mixin_test.dart new file mode 100644 index 00000000000..1240529db85 --- /dev/null +++ b/tests/language/mixin_legacy/mixin_test.dart @@ -0,0 +1,26 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M1 { + foo() => 42; +} + +class M2 = Object with M1; + +class S {} + +class C = S with M2; + +main() { + var c = new C(); + Expect.isTrue(c is S); + Expect.isTrue(c is M1); + Expect.isTrue(c is M2); + Expect.isTrue(c is C); + Expect.equals(42, c.foo()); +} diff --git a/tests/language/mixin_legacy/mixin_type_arguments_test.dart b/tests/language/mixin_legacy/mixin_type_arguments_test.dart new file mode 100644 index 00000000000..9698e2d4cfd --- /dev/null +++ b/tests/language/mixin_legacy/mixin_type_arguments_test.dart @@ -0,0 +1,99 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'package:expect/expect.dart' show Expect; + +@pragma("vm:entry-point") // Prevent obfuscation +class A {} + +@pragma("vm:entry-point") // Prevent obfuscation +class B {} + +@pragma("vm:entry-point") // Prevent obfuscation +class C {} + +@pragma("vm:entry-point") // Prevent obfuscation +class D {} + +@pragma("vm:entry-point") // Prevent obfuscation +class E {} + +@pragma("vm:entry-point") // Prevent obfuscation +class F {} + +@pragma("vm:entry-point") // Prevent obfuscation +class M1 { + m1() => "M1<$Tm1>"; +} + +@pragma("vm:entry-point") // Prevent obfuscation +class M2 { + m2() => "M2<$Tm2>"; +} + +@pragma("vm:entry-point") // Prevent obfuscation +class M3 { + m3() => "M3<$Tm3>"; +} + +@pragma("vm:entry-point") // Prevent obfuscation +class M4 { + m4() => "M4<$Tm4>"; +} + +@pragma("vm:entry-point") // Prevent obfuscation +class M5 { + m5() => "M5<$Tm5>"; +} + +class C1 = Object with M1, M2, M3, M4, M5; + +class C2 = Object with M1, M2, M3, M4, M5; + +class C3 = Object with M1, M2, M3, M4, M5; + +class C4 extends Object with M1, M2, M3, M4, M5 {} + +class C5 extends Object with M1, M2, M3, M4, M5 {} + +class C6 extends Object with M1, M2, M3, M4, M5 {} + +class C7 = Object with M1, M2, M3, M4, M5; + +class C8 extends Object with M1, M2, M3, M4, M5 {} + +class C9 = Object + with M1>, M2>, M3>, M4>, M5>; + +class CA extends Object + with M1>, M2>, M3>, M4>, M5> {} + +trace(x) => "${x.m1()}, ${x.m2()}, ${x.m3()}, ${x.m4()}, ${x.m5()}"; + +main() { + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C1())); + Expect.stringEquals("M1, M2, M3, M4, M5", trace(new C2())); + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C3())); + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C3())); + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C4())); + Expect.stringEquals("M1, M2, M3, M4, M5", trace(new C5())); + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C6())); + Expect.stringEquals( + "M1, M2, M3, M4, M5", trace(new C6())); + Expect.stringEquals("M1, M2, M3, M4, M5", trace(new C7())); + Expect.stringEquals("M1, M2, M3, M4, M5", trace(new C8())); + Expect.stringEquals( + "M1>, M2>, M3>, M4>, M5>", + trace(new C9())); + Expect.stringEquals( + "M1>, M2>, M3>, M4>, M5>", + trace(new CA())); +} diff --git a/tests/language/mixin_legacy/named_constructor_test.dart b/tests/language/mixin_legacy/named_constructor_test.dart new file mode 100644 index 00000000000..5a29c9cf369 --- /dev/null +++ b/tests/language/mixin_legacy/named_constructor_test.dart @@ -0,0 +1,32 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +var calls = []; + +abstract class A { + bool _done = true; + var a = calls.add('A()') as dynamic; +} + +abstract class B { + B.protected() { + calls.add('B.protected()'); + } +} + +class C extends B with A { + C() : super.protected() { + calls.add('C()'); + } +} + +void main() { + var c = new C(); + Expect.isTrue(c._done); + Expect.equals(calls.join(', '), 'A(), B.protected(), C()'); +} diff --git a/tests/language/mixin_legacy/naming_test.dart b/tests/language/mixin_legacy/naming_test.dart new file mode 100644 index 00000000000..a5d63010780 --- /dev/null +++ b/tests/language/mixin_legacy/naming_test.dart @@ -0,0 +1,53 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S {} + +class M1 {} + +class M2 {} + +class M3 {} + +class C = S with M1, M2, M3; + +class D extends S with M1, M2, M3 {} + +class S_M1 {} + +class S_M1_M2 {} + +main() { + var c = new C(); + Expect.isTrue(c is C); + Expect.isFalse(c is D); + Expect.isTrue(c is S); + Expect.isFalse(c is S_M1); + Expect.isFalse(c is S_M1_M2); + + var d = new D(); + Expect.isFalse(d is C); + Expect.isTrue(d is D); + Expect.isTrue(d is S); + Expect.isFalse(d is S_M1); + Expect.isFalse(d is S_M1_M2); + + var sm = new S_M1(); + Expect.isFalse(sm is C); + Expect.isFalse(sm is D); + Expect.isFalse(sm is S); + Expect.isTrue(sm is S_M1); + Expect.isFalse(sm is S_M1_M2); + + var smm = new S_M1_M2(); + Expect.isFalse(smm is C); + Expect.isFalse(smm is D); + Expect.isFalse(smm is S); + Expect.isFalse(smm is S_M1); + Expect.isTrue(smm is S_M1_M2); +} diff --git a/tests/language/mixin_legacy/only_for_rti_test.dart b/tests/language/mixin_legacy/only_for_rti_test.dart new file mode 100644 index 00000000000..dbe130270c4 --- /dev/null +++ b/tests/language/mixin_legacy/only_for_rti_test.dart @@ -0,0 +1,31 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Tester { + testGenericType(x) { + return x is T; + } +} + +abstract class A = B with C; + +class B {} + +class C {} + +class X extends Y with Z {} + +class Y {} + +class Z {} + +main() { + // Classes A and X are only used as generic arguments. + Expect.isFalse(new Tester().testGenericType(new Object())); + Expect.isFalse(new Tester().testGenericType(new Object())); +} diff --git a/tests/language/mixin_legacy/override_regression_test.dart b/tests/language/mixin_legacy/override_regression_test.dart new file mode 100644 index 00000000000..b266da79b86 --- /dev/null +++ b/tests/language/mixin_legacy/override_regression_test.dart @@ -0,0 +1,27 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class C0 { + int m1() => 5; + int m2() => m1(); +} + +class C1 = Object with C0; + +class D { + int m1() => 7; +} + +class E0 extends C0 with D {} + +class E1 extends C1 with D {} + +main() { + Expect.equals(7, new E0().m2()); + Expect.equals(7, new E1().m2()); +} diff --git a/tests/language/mixin_legacy/prefix_lib.dart b/tests/language/mixin_legacy/prefix_lib.dart new file mode 100644 index 00000000000..2df87a82874 --- /dev/null +++ b/tests/language/mixin_legacy/prefix_lib.dart @@ -0,0 +1,13 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +library mixin_prefix_lib; + +import "dart:convert"; + +mixin MixinClass { + String bar() => json.encode({'a': 1}); +} diff --git a/tests/language/mixin_legacy/prefix_test.dart b/tests/language/mixin_legacy/prefix_test.dart new file mode 100644 index 00000000000..024739d46d6 --- /dev/null +++ b/tests/language/mixin_legacy/prefix_test.dart @@ -0,0 +1,19 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Regression test for issue 11891. + +import "package:expect/expect.dart"; +import "prefix_lib.dart"; + +class A extends Object with MixinClass { + String baz() => bar(); +} + +void main() { + var a = new A(); + Expect.equals('{"a":1}', a.baz()); +} diff --git a/tests/language/mixin_legacy/proto_test.dart b/tests/language/mixin_legacy/proto_test.dart new file mode 100644 index 00000000000..691ff649f7b --- /dev/null +++ b/tests/language/mixin_legacy/proto_test.dart @@ -0,0 +1,42 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Tests that a program in csp mode doesn't access the prototype chain +// on platforms that don't support direct access to __proto__. +// This test is most useful with --csp and on a platform that doesn't support +// __proto__ access (such as Rhino). +// See http://dartbug.com/27290 . + +import 'package:expect/expect.dart'; + +class A { + var x; + foo() => 44; + bar() => 22; +} + +class B { + var y; + foo() => 42; +} + +class C extends A with B { + var z; + bar() => 499; +} + +@pragma('dart2js:noInline') +@pragma('dart2js:assumeDynamic') +confuse(x) => x; + +main() { + var all = [new A(), new B(), new C()]; + Expect.equals(44, confuse(all[0]).foo()); + Expect.equals(22, confuse(all[0]).bar()); + Expect.equals(42, confuse(all[1]).foo()); + Expect.equals(42, confuse(all[2]).foo()); + Expect.equals(499, confuse(all[2]).bar()); +} diff --git a/tests/language/mixin_legacy/recursive_mixin_test.dart b/tests/language/mixin_legacy/recursive_mixin_test.dart new file mode 100644 index 00000000000..771e154cd36 --- /dev/null +++ b/tests/language/mixin_legacy/recursive_mixin_test.dart @@ -0,0 +1,28 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class A { + bool foo(T x) => true; +} + +class B extends Object with A, C {} + +// Tests #31290 +class C {} + +main() { + var b = new B(); + Expect.isTrue(b is B); + Expect.isTrue(b is A); + Expect.isTrue(b is C); + + // Verify that runtime checking enforces A instead of A + dynamic d = b; + Expect.isTrue(d.foo(b)); + Expect.throws(() => d.foo(42)); +} diff --git a/tests/language/mixin_legacy/regress_11398_test.dart b/tests/language/mixin_legacy/regress_11398_test.dart new file mode 100644 index 00000000000..fe11e62431a --- /dev/null +++ b/tests/language/mixin_legacy/regress_11398_test.dart @@ -0,0 +1,46 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +void main() { + var hva = new HasValueA(); + hva.value = '42'; + Expect.equals('42', hva.value); + + var hvb = new HasValueB(); + hvb.value = '87'; + Expect.equals('87', hvb.value); + + var hvc = new HasValueC(); + hvc.value = '99'; + Expect.equals('99', hvc.value); +} + +abstract class Delegate { + String invoke(String value); +} + +abstract class DelegateMixin { + String invoke(String value) => value; +} + +abstract class HasValueMixin implements Delegate { + String _value = ''; + set value(String value) { + _value = invoke(value); + } + + String get value => _value; +} + +class HasValueA extends Object with HasValueMixin, DelegateMixin {} + +class HasValueB extends Object with DelegateMixin, HasValueMixin {} + +class HasValueC extends Object with HasValueMixin { + String invoke(String value) => value; +} diff --git a/tests/language/mixin_legacy/regress_13688_test.dart b/tests/language/mixin_legacy/regress_13688_test.dart new file mode 100644 index 00000000000..ed12af4beb6 --- /dev/null +++ b/tests/language/mixin_legacy/regress_13688_test.dart @@ -0,0 +1,20 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class ComparableMixin { + e() { + return E; + } +} + +class KUID extends Object with ComparableMixin {} + +main() { + var kuid = new KUID(); + Expect.equals(kuid.runtimeType.toString(), kuid.e().toString()); +} diff --git a/tests/language/mixin_legacy/regress_47645_test.dart b/tests/language/mixin_legacy/regress_47645_test.dart new file mode 100644 index 00000000000..28a991407ae --- /dev/null +++ b/tests/language/mixin_legacy/regress_47645_test.dart @@ -0,0 +1,21 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +// Regression test for https://github.com/dart-lang/sdk/issues/47645. +// To reproduce the issue the class declaration must appear before the mixin +// declaration. +class C with M> {} + +mixin M { + bool fn() => true; +} + +void main() { + var c = C(); + Expect.isTrue(c.fn()); +} diff --git a/tests/language/mixin_legacy/regress_flutter_55345_const_test.dart b/tests/language/mixin_legacy/regress_flutter_55345_const_test.dart new file mode 100644 index 00000000000..b98a4741277 --- /dev/null +++ b/tests/language/mixin_legacy/regress_flutter_55345_const_test.dart @@ -0,0 +1,40 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verifies that references to deduplicated mixins are properly updated +// in types which are only accessible through constants. +// Regression test for https://github.com/flutter/flutter/issues/55345. + +class Diagnosticable {} + +class SomeClass with Diagnosticable {} + +class State with Diagnosticable { + const State(); +} + +class StateA extends State { + const StateA(); +} + +class StateB extends State { + const StateB(); +} + +const c1 = StateA() as dynamic; +const c2 = StateB(); + +main() { + print(const [ + { + (c1 ?? c2): [ + [c1 ?? c2] + ] + }, + 'abc' + ]); + // No compile time or runtime errors. +} diff --git a/tests/language/mixin_legacy/regress_flutter_55345_test.dart b/tests/language/mixin_legacy/regress_flutter_55345_test.dart new file mode 100644 index 00000000000..da142e18ba8 --- /dev/null +++ b/tests/language/mixin_legacy/regress_flutter_55345_test.dart @@ -0,0 +1,44 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verifies that references to deduplicated mixins are properly updated. +// Regression test for https://github.com/flutter/flutter/issues/55345. + +class Diagnosticable {} + +class SomeClass with Diagnosticable {} + +class State with Diagnosticable {} + +class StateA extends State {} + +class StateB extends State {} + +StateA? a = StateA(); +StateB? b = StateB(); + +List foo(T x) { + print(T); + return [x]; +} + +T Function(T) bar(T x) { + print(T); + + return (T y) { + print(S); + print(y); + return y; + }; +} + +main() { + var x2 = a ?? b; + var x3 = foo(x2); + var x4 = bar(x3); + x4(x3); + // No compile time or runtime errors. +} diff --git a/tests/language/mixin_legacy/regress_flutter_66859_1_test.dart b/tests/language/mixin_legacy/regress_flutter_66859_1_test.dart new file mode 100644 index 00000000000..abebd940e51 --- /dev/null +++ b/tests/language/mixin_legacy/regress_flutter_66859_1_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verifies that mixin supertypes are properly maintained even if marked as +// deferred (e.g., in a circular hierarchy). +// Regression test for: https://github.com/flutter/flutter/issues/66859 + +import "package:expect/expect.dart"; + +mixin M {} + +mixin N {} + +class A extends B with M, N {} + +class B {} + +class C extends A {} + +class Z extends B with M {} + +main() { + var z = Z(); + Expect.isTrue(z is B); + Expect.isTrue(z is M); + var a = A(); + Expect.isTrue(a is M); + Expect.isTrue(a is N); + Expect.isTrue(a is B); +} diff --git a/tests/language/mixin_legacy/regress_flutter_66859_2_test.dart b/tests/language/mixin_legacy/regress_flutter_66859_2_test.dart new file mode 100644 index 00000000000..1b6c09d53f6 --- /dev/null +++ b/tests/language/mixin_legacy/regress_flutter_66859_2_test.dart @@ -0,0 +1,39 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Verifies that mixin supertypes are properly maintained even if marked as +// deferred (e.g., in a circular hierarchy). +// Regression test for: https://github.com/flutter/flutter/issues/66859 + +import "package:expect/expect.dart"; + +mixin X {} +mixin Y {} +mixin Z {} + +class A extends B with X {} + +class C extends A with Z {} + +class B extends Object with Y {} + +main() { + var a = A(); + var b = B(); + var c = C(); + Expect.isTrue(a is A); + Expect.isTrue(a is B); + Expect.isTrue(a is X); + Expect.isTrue(a is Y); + Expect.isTrue(c is C); + Expect.isTrue(c is A); + Expect.isTrue(c is B); + Expect.isTrue(c is X); + Expect.isTrue(c is Y); + Expect.isTrue(c is Z); + Expect.isTrue(b is B); + Expect.isTrue(b is Y); +} diff --git a/tests/language/mixin_legacy/substitution_test.dart b/tests/language/mixin_legacy/substitution_test.dart new file mode 100644 index 00000000000..8bba89093e1 --- /dev/null +++ b/tests/language/mixin_legacy/substitution_test.dart @@ -0,0 +1,28 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test that mixins don't interfere with type variable substitution. + +import '../dynamic_type_helper.dart'; + +class B { + B(T x); +} + +class M {} + +class A extends B with M { + A(T x) : super(x); // This line must be warning free. +} + +class C = B with M; + +main() { + new A(null); + new C(''); + dynamic value = 0; + checkDynamicTypeError(() => new C(value)); +} diff --git a/tests/language/mixin_legacy/super_2_test.dart b/tests/language/mixin_legacy/super_2_test.dart new file mode 100644 index 00000000000..a3a1b6cfbd3 --- /dev/null +++ b/tests/language/mixin_legacy/super_2_test.dart @@ -0,0 +1,43 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class B { + // 'super' resolves to Object, and in some tests, multiple points in the + // inheritance chain. + toString() => 'B(' + super.toString() + ')'; +} + +class R { + toString() => 'R[' + super.toString() + ']'; +} + +class D extends R with B { + toString() => 'D<' + super.toString() + '>'; +} + +class E extends D with B { + toString() => 'E{' + super.toString() + '}'; +} + +class F = R with B, B; + +class G extends F with B { + toString() => 'G{' + super.toString() + '}'; +} + +main() { + check(object, String expected) { + Expect.equals(expected, object.toString()); + } + + check(B(), "B(Instance of '$B')"); + check(R(), "R[Instance of '$R']"); + check(D(), "D"); + check(E(), "E{B(D)}"); + check(G(), "G{B(B(B(R[Instance of '$G'])))}"); +} diff --git a/tests/language/mixin_legacy/super_bound_runtime_test.dart b/tests/language/mixin_legacy/super_bound_runtime_test.dart new file mode 100644 index 00000000000..c6ee2744013 --- /dev/null +++ b/tests/language/mixin_legacy/super_bound_runtime_test.dart @@ -0,0 +1,30 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class M {} + +class N {} + +class S {} + +class MNA extends S> + with M, N, List> {} + +class MNA2 = S> with M, N, List>; + +main() { + new MNA(); + new MNA2(); + + // Type parameter U of M must extend type parameter V, but + // type argument num is not a subtype of int. + + // Type parameter U of M must extend type parameter V, but + // type argument num is not a subtype of int. +} diff --git a/tests/language/mixin_legacy/super_bound_test.dart b/tests/language/mixin_legacy/super_bound_test.dart new file mode 100644 index 00000000000..cb8b7739417 --- /dev/null +++ b/tests/language/mixin_legacy/super_bound_test.dart @@ -0,0 +1,37 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class M {} + +class N {} + +class S {} + +class MNA extends S> + with M, N, List> {} + +class MNA2 = S> with M, N, List>; + +main() { + new MNA(); + new MNA2(); + + // Type parameter U of M must extend type parameter V, but + // type argument num is not a subtype of int. + new MNA(); + // ^ + // [cfe] Type argument 'num' doesn't conform to the bound 'U' of the type variable 'V' on 'MNA'. + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.TYPE_ARGUMENT_NOT_MATCHING_BOUNDS + + // Type parameter U of M must extend type parameter V, but + // type argument num is not a subtype of int. + new MNA2(); + // ^ + // [cfe] Type argument 'num' doesn't conform to the bound 'U' of the type variable 'V' on 'MNA2'. + // ^^^ + // [analyzer] COMPILE_TIME_ERROR.TYPE_ARGUMENT_NOT_MATCHING_BOUNDS +} diff --git a/tests/language/mixin_legacy/super_constructor2_test.dart b/tests/language/mixin_legacy/super_constructor2_test.dart new file mode 100644 index 00000000000..dcbe5d5cf4c --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor2_test.dart @@ -0,0 +1,41 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + var i, j; + Base.ctor1(int i, this.j) : this.i = i + 7; + Base.ctor2(int i, this.j) : this.i = i + 8; +} + +abstract class M { + get i; + get j; + int k = 42; + foo() => i + j; +} + +class C extends Base with M { + int l = 131; + C.ctor1() : super.ctor1(1, 13); + C.ctor2() : super.ctor2(1, 13); +} + +main() { + C c1 = new C.ctor1(); + Expect.equals(8, c1.i); + Expect.equals(13, c1.j); + Expect.equals(42, c1.k); + Expect.equals(131, c1.l); + Expect.equals(21, c1.foo()); + C c2 = new C.ctor2(); + Expect.equals(9, c2.i); + Expect.equals(13, c2.j); + Expect.equals(42, c2.k); + Expect.equals(131, c2.l); + Expect.equals(22, c2.foo()); +} diff --git a/tests/language/mixin_legacy/super_constructor_default_test.dart b/tests/language/mixin_legacy/super_constructor_default_test.dart new file mode 100644 index 00000000000..d0b4ce3f668 --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor_default_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + int i, j; + Base(int i, this.j) : this.i = i + 7; +} + +abstract class M { + int get i; + int get j; + int k = 42; + foo() => i + j; +} + +class C extends Base with M { + int l = 131; + C() : super(1, 13); +} + +main() { + C c = new C(); + Expect.equals(8, c.i); + Expect.equals(13, c.j); + Expect.equals(21, c.foo()); + Expect.equals(42, c.k); + Expect.equals(131, c.l); +} diff --git a/tests/language/mixin_legacy/super_constructor_multiple_test.dart b/tests/language/mixin_legacy/super_constructor_multiple_test.dart new file mode 100644 index 00000000000..ec55380ca02 --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor_multiple_test.dart @@ -0,0 +1,24 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + int i; + S.foo() : i = 1742; +} + +class M1 {} + +class M2 {} + +class C extends S with M1, M2 { + C.foo() : super.foo(); +} + +main() { + Expect.equals(1742, new C.foo().i); +} diff --git a/tests/language/mixin_legacy/super_constructor_named_test.dart b/tests/language/mixin_legacy/super_constructor_named_test.dart new file mode 100644 index 00000000000..a70aeb66714 --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor_named_test.dart @@ -0,0 +1,41 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + int? i, j; + Base.ctor(int? this.i + , {int? this.j = 10} // //# 01: ok + ) { + if (j == null) { + j = 10; + } + } +} + +abstract class M { + int? get i; + int? get j; + int k = 42; + foo() => i! + j!; +} + +class C extends Base with M { + int l = 131; + C.foo() : super.ctor(1, j: 13); //# 01: continued + C.bar() : super.ctor(1); +} + +main() { + C c1 = new C.foo(); // //# 01: continued + C c2 = new C.bar(); + Expect.equals(1, c2.i); + Expect.equals(10, c2.j); + Expect.equals(11, c2.foo()); + Expect.equals(42, c2.k); + Expect.equals(131, c2.l); +} diff --git a/tests/language/mixin_legacy/super_constructor_positionals_test.dart b/tests/language/mixin_legacy/super_constructor_positionals_test.dart new file mode 100644 index 00000000000..422d41f2a88 --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor_positionals_test.dart @@ -0,0 +1,40 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + int? i, j; + Base.ctor( + int? this.i, + [ // //# 01: ok + int? this.j + ] // //# 01: continued + ); +} + +abstract class M { + int? get i; + int? get j; + int k = 42; + foo() => i! + j!; +} + +class C extends Base with M { + int l = 131; + C.foo() : super.ctor(1, 13); + C.bar() : super.ctor(1); // //# 01: continued +} + +main() { + C c1 = new C.foo(); + Expect.equals(1, c1.i); + Expect.equals(13, c1.j); + Expect.equals(14, c1.foo()); + Expect.equals(42, c1.k); + Expect.equals(131, c1.l); + C c2 = new C.bar(); // //# 01: continued +} diff --git a/tests/language/mixin_legacy/super_constructor_test.dart b/tests/language/mixin_legacy/super_constructor_test.dart new file mode 100644 index 00000000000..23cc3e849bf --- /dev/null +++ b/tests/language/mixin_legacy/super_constructor_test.dart @@ -0,0 +1,33 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class Base { + int i, j; + Base.ctor(int i, this.j) : this.i = i + 7; +} + +abstract class M { + int get i; + int get j; + int k = 42; + foo() => i + j; +} + +class C extends Base with M { + int l = 131; + C() : super.ctor(1, 13); +} + +main() { + C c = new C(); + Expect.equals(8, c.i); + Expect.equals(13, c.j); + Expect.equals(42, c.k); + Expect.equals(131, c.l); + Expect.equals(21, c.foo()); +} diff --git a/tests/language/mixin_legacy/super_test.dart b/tests/language/mixin_legacy/super_test.dart new file mode 100644 index 00000000000..cec08449325 --- /dev/null +++ b/tests/language/mixin_legacy/super_test.dart @@ -0,0 +1,106 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class MS { + foo() { + return "MS<$T>.foo\n"; + } +} + +mixin M on MS> { + foo() { + return super.foo() + "M<$T>.foo\n"; + } +} + +class NS { + foo() { + return "NS<$T>.foo\n"; + } +} + +mixin N on NS> { + foo() { + return super.foo() + "N<$T>.foo\n"; + } +} + +class S implements MS>, NS> { + foo() { + return "S<$T,$V,$W>.foo\n"; + } +} + +class SM = S with M; + +class MNA1 extends S with M, N { + foo() { + return super.foo() + "MNA1<$U, $V, $W>.foo\n"; + } +} + +class MNA2 extends SM with N { + foo() { + return super.foo() + "MNA2<$U, $V, $W>.foo\n"; + } +} + +class MNA3 extends S with M, N { + foo() { + return super.foo() + "MNA3<$U, $V, $W>.foo\n"; + } +} + +abstract class Base { + static String log = ''; + Base() { + log += 'Base()\n'; + } +} + +mixin Foo on Base { + var x = Base.log += 'Foo.x\n'; +} + +mixin Bar on Base { + var y = Base.log += 'Bar.y\n'; +} + +class Derived extends Base with Foo, Bar { + String get log => Base.log; +} + +main() { + Expect.equals( + "S.foo\n" + "M.foo\n", + SM().foo()); + Expect.equals( + "S.foo\n" + "M.foo\n" + "N.foo\n" + "MNA1.foo\n", + MNA1().foo()); + Expect.equals( + "S.foo\n" + "M.foo\n" + "N.foo\n" + "MNA2.foo\n", + MNA2().foo()); + Expect.equals( + "S.foo\n" + "M.foo\n" + "N.foo\n" + "MNA3.foo\n", + MNA3().foo()); + Expect.equals( + "Bar.y\n" + "Foo.x\n" + "Base()\n", + Derived().log); +} diff --git a/tests/language/mixin_legacy/super_use_test.dart b/tests/language/mixin_legacy/super_use_test.dart new file mode 100644 index 00000000000..51e89f23853 --- /dev/null +++ b/tests/language/mixin_legacy/super_use_test.dart @@ -0,0 +1,67 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M {} + +class P0 { + foo() { + super.toString(); + + void inner() { + super.toString(); + } + + inner(); + + (() { + super.toString(); + })(); + + return 42; + } +} + +class P1 { + bar() { + super.toString(); + return 87; + } + + // The test method is strategically placed here to try to force the + // P1 class and its bar method to be resolved before resolving the + // mixin applications. + test() { + new C(); + var d = new D(); + var e = new E(); + var f = new F(); + Expect.equals(42, d.foo()); + Expect.equals(87, e.bar()); + Expect.equals(99, f.baz()); + } +} + +class P2 { + baz() { + super.toString(); + return 99; + } +} + +class C = Object with M; +class D = Object with P0; +class E = Object with M, P1; +class F = Object with P2, M; + +main() { + var p1 = new P1(); + var p2 = new P2(); + Expect.equals(87, p1.bar()); + p1.test(); + Expect.equals(99, p2.baz()); +} diff --git a/tests/language/mixin_legacy/super_with_initializer_test.dart b/tests/language/mixin_legacy/super_with_initializer_test.dart new file mode 100644 index 00000000000..107033d1618 --- /dev/null +++ b/tests/language/mixin_legacy/super_with_initializer_test.dart @@ -0,0 +1,32 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +/// Regression test for mixin overrides (dartbug.com/44636). +/// +/// Prior to the fix, B's initializer was accidentally being applied on the +/// overridden definition in C, and as a result, the program would stack +/// overflow. +import 'package:expect/expect.dart'; + +class A = B with C; + +mixin M {} + +abstract class B with M { + Object _test = "a"; +} + +mixin C on B, M { + @override + Object get _test => super._test; + + @override + set _test(Object value) { + super._test = value; + } +} + +main() => Expect.equals("a", A()._test); diff --git a/tests/language/mixin_legacy/superclass_runtime_test.dart b/tests/language/mixin_legacy/superclass_runtime_test.dart new file mode 100644 index 00000000000..8f1f17f7637 --- /dev/null +++ b/tests/language/mixin_legacy/superclass_runtime_test.dart @@ -0,0 +1,94 @@ +// TODO(multitest): This was automatically migrated from a multitest and may +// contain strange or dead code. + +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S1 extends Object {} + +class S2 extends S0 {} + +class M0 {} + +class M1 extends Object {} + +mixin M2 on M0 {} + +class C00 = S0 with M0; +class C01 = S0 with M1; + +class C03 = S0 with M0, M1; +class C04 = S0 with M0, M2; + +class C10 = S1 with M0; +class C11 = S1 with M1; + +class C13 = S1 with M0, M1; +class C14 = S1 with M0, M2; + +class C20 = S2 with M0; +class C21 = S2 with M1; + +class C23 = S2 with M0, M1; +class C24 = S2 with M0, M2; + +class D00 extends S0 with M0 {} + +class D01 extends S0 with M1 {} + +class D03 extends S0 with M0, M1 {} + +class D04 extends S0 with M0, M2 {} + +class D10 extends S1 with M0 {} + +class D11 extends S1 with M1 {} + +class D13 extends S1 with M0, M1 {} + +class D14 extends S1 with M0, M2 {} + +class D20 extends S2 with M0 {} + +class D21 extends S2 with M1 {} + +class D23 extends S2 with M0, M1 {} + +class D24 extends S2 with M0, M2 {} + +main() { + new C00(); + new C01(); + new C03(); + new C04(); + + new C10(); + new C11(); + new C13(); + new C14(); + + new C20(); + new C21(); + new C23(); + new C24(); + + new D00(); + new D01(); + new D03(); + new D04(); + + new D10(); + new D11(); + new D13(); + new D14(); + + new D20(); + new D21(); + new D23(); + new D24(); +} diff --git a/tests/language/mixin_legacy/superclass_test.dart b/tests/language/mixin_legacy/superclass_test.dart new file mode 100644 index 00000000000..d4ac492d34a --- /dev/null +++ b/tests/language/mixin_legacy/superclass_test.dart @@ -0,0 +1,220 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S0 {} + +class S1 extends Object {} + +class S2 extends S0 {} + +class M0 {} + +class M1 extends Object {} + +mixin M2 on M0 {} + +class C00 = S0 with M0; +class C01 = S0 with M1; +class C02 = S0 with M2; +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C03 = S0 with M0, M1; +class C04 = S0 with M0, M2; +class C05 = S0 with M2, M0; +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C06 = S0 with M1, M2; +// ^ +// [cfe] '_C06&S0&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C07 = S0 with M2, M1; +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class C10 = S1 with M0; +class C11 = S1 with M1; +class C12 = S1 with M2; +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C13 = S1 with M0, M1; +class C14 = S1 with M0, M2; +class C15 = S1 with M2, M0; +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C16 = S1 with M1, M2; +// ^ +// [cfe] '_C16&S1&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C17 = S1 with M2, M1; +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class C20 = S2 with M0; +class C21 = S2 with M1; +class C22 = S2 with M2; +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C23 = S2 with M0, M1; +class C24 = S2 with M0, M2; +class C25 = S2 with M2, M0; +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C26 = S2 with M1, M2; +// ^ +// [cfe] '_C26&S2&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE +class C27 = S2 with M2, M1; +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D00 extends S0 with M0 {} + +class D01 extends S0 with M1 {} + +class D02 extends S0 with M2 {} +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D03 extends S0 with M0, M1 {} + +class D04 extends S0 with M0, M2 {} + +class D05 extends S0 with M2, M0 {} +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D06 extends S0 with M1, M2 {} +// ^ +// [cfe] '_D06&S0&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D07 extends S0 with M2, M1 {} +// ^ +// [cfe] 'S0' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D10 extends S1 with M0 {} + +class D11 extends S1 with M1 {} + +class D12 extends S1 with M2 {} +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D13 extends S1 with M0, M1 {} + +class D14 extends S1 with M0, M2 {} + +class D15 extends S1 with M2, M0 {} +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D16 extends S1 with M1, M2 {} +// ^ +// [cfe] '_D16&S1&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D17 extends S1 with M2, M1 {} +// ^ +// [cfe] 'S1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D20 extends S2 with M0 {} + +class D21 extends S2 with M1 {} + +class D22 extends S2 with M2 {} +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D23 extends S2 with M0, M1 {} + +class D24 extends S2 with M0, M2 {} + +class D25 extends S2 with M2, M0 {} +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D26 extends S2 with M1, M2 {} +// ^ +// [cfe] '_D26&S2&M1' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +class D27 extends S2 with M2, M1 {} +// ^ +// [cfe] 'S2' doesn't implement 'M0' so it can't be used with 'M2'. +// ^^ +// [analyzer] COMPILE_TIME_ERROR.MIXIN_APPLICATION_NOT_IMPLEMENTED_INTERFACE + +main() { + new C00(); + new C01(); + new C03(); + new C04(); + + new C10(); + new C11(); + new C13(); + new C14(); + + new C20(); + new C21(); + new C23(); + new C24(); + + new D00(); + new D01(); + new D03(); + new D04(); + + new D10(); + new D11(); + new D13(); + new D14(); + + new D20(); + new D21(); + new D23(); + new D24(); +} diff --git a/tests/language/mixin_legacy/supertype_subclass2_test.dart b/tests/language/mixin_legacy/supertype_subclass2_test.dart new file mode 100644 index 00000000000..cfee7c2e37a --- /dev/null +++ b/tests/language/mixin_legacy/supertype_subclass2_test.dart @@ -0,0 +1,30 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class B {} + +class C {} + +class D {} + +class E extends B with C implements D {} + +class F extends E {} + +// M is mixed onto E which implements B, C and D. +mixin M // + on B //# 01: ok + on C //# 02: ok + on D //# 03: ok + on E //# 04: ok + on F //# 05: compile-time error +{} + +class A extends E with M {} + +main() { + new A(); +} diff --git a/tests/language/mixin_legacy/supertype_subclass_test.dart b/tests/language/mixin_legacy/supertype_subclass_test.dart new file mode 100644 index 00000000000..eadf8bc17c2 --- /dev/null +++ b/tests/language/mixin_legacy/supertype_subclass_test.dart @@ -0,0 +1,30 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class B {} + +class C {} + +class D {} + +class E extends B with C implements D {} + +class F extends E {} + +// M is mixed onto E which implements B, C and D. +mixin M // + on B //# 01: ok + on C //# 02: ok + on D //# 03: ok + on E //# 04: ok + on F //# 05: compile-time error +{} + +class A = E with M; + +main() { + new A(); +} diff --git a/tests/language/mixin_legacy/this_use_test.dart b/tests/language/mixin_legacy/this_use_test.dart new file mode 100644 index 00000000000..31ebf44b847 --- /dev/null +++ b/tests/language/mixin_legacy/this_use_test.dart @@ -0,0 +1,32 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Test that [:this:] in a class A used as a mixin in class D knows it can be an +// instance of D. + +import "package:expect/expect.dart"; + +class A { + foo() => bar(); // Implicit use of [:this:] + bar() => 42; +} + +class B {} + +class C = B with A; + +class D extends C { + bar() => 54; +} + +class E extends A { + bar() => 68; +} + +main() { + Expect.equals(54, new D().foo()); + Expect.equals(68, new E().foo()); +} diff --git a/tests/language/mixin_legacy/type_parameter1_test.dart b/tests/language/mixin_legacy/type_parameter1_test.dart new file mode 100644 index 00000000000..90f3490fa80 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter1_test.dart @@ -0,0 +1,25 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class Mixin1 {} + +abstract class Mixin2 {} + +class A {} + +class MyTypedef = A with Mixin1, Mixin2; + +class B extends MyTypedef {} + +main() { + var b = new B(); + Expect.isTrue(b is Mixin1); + Expect.isTrue(b is! Mixin1); + Expect.isTrue(b is Mixin2); + Expect.isTrue(b is! Mixin2); +} diff --git a/tests/language/mixin_legacy/type_parameter2_test.dart b/tests/language/mixin_legacy/type_parameter2_test.dart new file mode 100644 index 00000000000..3a1662cf742 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter2_test.dart @@ -0,0 +1,29 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class Mixin1 {} + +abstract class Mixin2 {} + +class A { + A(foo); +} + +class MyTypedef = A with Mixin1, Mixin2; + +class B extends MyTypedef { + B(foo) : super(foo); +} + +main() { + var b = new B(null); + Expect.isTrue(b is Mixin1); + Expect.isTrue(b is! Mixin1); + Expect.isTrue(b is Mixin2); + Expect.isTrue(b is! Mixin2); +} diff --git a/tests/language/mixin_legacy/type_parameter3_test.dart b/tests/language/mixin_legacy/type_parameter3_test.dart new file mode 100644 index 00000000000..6984ffdb3b3 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter3_test.dart @@ -0,0 +1,27 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class Mixin1 {} + +abstract class Mixin2 {} + +class A { + A(foo); +} + +class B extends A with Mixin1, Mixin2 { + B(foo) : super(foo); +} + +main() { + var b = new B(null); + Expect.isTrue(b is Mixin1); + Expect.isTrue(b is! Mixin1); + Expect.isTrue(b is Mixin2); + Expect.isTrue(b is! Mixin2); +} diff --git a/tests/language/mixin_legacy/type_parameter4_test.dart b/tests/language/mixin_legacy/type_parameter4_test.dart new file mode 100644 index 00000000000..7015e0f8810 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter4_test.dart @@ -0,0 +1,26 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class R {} + +class M implements R {} + +class B1 {} + +class B2 {} + +class A1 extends B1 with M {} + +class A2 = B2 with M; + +main() { + var a1 = new A1(); + Expect.isTrue(a1 is R); + var a2 = new A2(); + Expect.isTrue(a2 is R); +} diff --git a/tests/language/mixin_legacy/type_parameter5_test.dart b/tests/language/mixin_legacy/type_parameter5_test.dart new file mode 100644 index 00000000000..6e06693580f --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter5_test.dart @@ -0,0 +1,28 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class MixinA { + T? intField; +} + +class MixinB { + S? stringField; +} + +class MixinC { + U? listField; + V? mapField; +} + +class C extends Object with MixinA, MixinB, MixinC {} + +void main() { + var c = new C(); + c.intField = 0; + c.stringField = ''; + c.listField = []; + c.mapField = {}; +} diff --git a/tests/language/mixin_legacy/type_parameter6_test.dart b/tests/language/mixin_legacy/type_parameter6_test.dart new file mode 100644 index 00000000000..29d9c37e745 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter6_test.dart @@ -0,0 +1,19 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class A {} + +class B { + int? foo(S s) => null; +} + +class C extends A with B {} + +main() { + var list = ['foo']; + var c = new C(); + list.map(c.foo); +} diff --git a/tests/language/mixin_legacy/type_parameter_inference_error_test.dart b/tests/language/mixin_legacy/type_parameter_inference_error_test.dart new file mode 100644 index 00000000000..03499446ffd --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter_inference_error_test.dart @@ -0,0 +1,26 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +abstract class A {} + +class B {} + +mixin M on A {} + +// No matching class from which to infer the type parameter of M +class C extends Object with M {} //# 01: compile-time error + +class C = Object with M; //# 02: compile-time error + +// Satisfying the constraint with an "implements" clause is not sufficient +class C extends Object with M implements A {} //# 03: compile-time error + +class C = Object with M implements A; //# 04: compile-time error + +// Mixin works when used correctly. +class D = A with M; + +main() {} diff --git a/tests/language/mixin_legacy/type_parameter_inference_previous_mixin_test.dart b/tests/language/mixin_legacy/type_parameter_inference_previous_mixin_test.dart new file mode 100644 index 00000000000..05ab1e43449 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter_inference_previous_mixin_test.dart @@ -0,0 +1,39 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class A { + // This is ok because type inference will ensure that in C, A and M are + // instantiated with the same T. + T f(T x) => x; //# 01: ok +} + +class B {} + +abstract class M1 implements A {} + +mixin M2 on A { + T f(T x) => x; + T g(T x) => x; + Type h() => T; +} + +// Inferred as `class C extends Object with M1, M2` +class C extends Object with M1, M2 {} + +main() { + C c = new C(); + + // M is instantiated with B, so C.g has type (B) -> B. + B Function(B) x = c.g; //# 02: ok + Null Function(Null) x = c.g; //# 03: compile-time error + Object Function(Object) x = c.g; //# 04: compile-time error + + // And verify that the runtime system has the right type for the type + // parameter + Expect.equals(c.h(), B); //# 05: ok +} diff --git a/tests/language/mixin_legacy/type_parameter_inference_test.dart b/tests/language/mixin_legacy/type_parameter_inference_test.dart new file mode 100644 index 00000000000..04a6c10d405 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameter_inference_test.dart @@ -0,0 +1,75 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +abstract class A { + // This is ok because type inference will ensure that in C, A and M are + // instantiated with the same T. + T f(T x) => x; //# 01: ok +} + +class B {} + +mixin M1 on A { + T f(T x) => x; + T g(T x) => x; + Type h() => T; +} + +class M2 { + T g(T x) => x; + Type h() => T; +} + +// Inferred as `class C extends A with M1` +class C extends A with M1 {} + +// Inferred as `class D = A with M1` +class D = A with M1; + +// Inferred as `class E extends Object with M2` +class E extends Object with M2 {} + +// Ok because a type parameter is supplied +class F extends Object with M2 {} + +main() { + C c = new C(); + D d = new D(); + E e = new E(); + F f = new F(); + + // M1 is instantiated with B, so C.g has type (B) -> B. + B Function(B) x = c.g; //# 02: ok + B Function(B) x = d.g; //# 03: ok + Null Function(Null) x = c.g; //# 04: compile-time error + Null Function(Null) x = d.g; //# 05: compile-time error + Object Function(Object) x = c.g; //# 06: compile-time error + Object Function(Object) x = d.g; //# 07: compile-time error + + // And verify that the runtime system has the right type for the type + // parameter + Expect.equals(c.h(), B); //# 08: ok + Expect.equals(c.h(), B); //# 09: ok + + // M2 is instantiated with dynamic, so E.g has type (dynamic) -> dynamic. + dynamic Function(dynamic) x = e.g; //# 10: ok + B Function(B) x = e.g; //# 11: compile-time error + + // And verify that the runtime system has the right type for the type + // parameter + Expect.equals(e.h(), dynamic); //# 12: ok + + // M2 is instantiated with B, so F.g has type (B) -> B. + B Function(B) x = f.g; //# 13: ok + Null Function(Null) x = f.g; //# 14: compile-time error + Object Function(Object) x = f.g; //# 15: compile-time error + + // And verify that the runtime system has the right type for the type + // parameter + Expect.equals(f.h(), B); //# 16: ok +} diff --git a/tests/language/mixin/illegal_cycles_runtime_test.dart b/tests/language/mixin_legacy/type_parameters_errors_runtime_test.dart similarity index 53% rename from tests/language/mixin/illegal_cycles_runtime_test.dart rename to tests/language/mixin_legacy/type_parameters_errors_runtime_test.dart index cd5bbfe9582..b388cbb258d 100644 --- a/tests/language/mixin/illegal_cycles_runtime_test.dart +++ b/tests/language/mixin_legacy/type_parameters_errors_runtime_test.dart @@ -1,42 +1,24 @@ // TODO(multitest): This was automatically migrated from a multitest and may // contain strange or dead code. -// Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file +// Copyright (c) 2023, 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 M {} - - - - - - - - - - - - +// @dart=2.19 +class S {} +class M {} +class A extends S with M {} +class F = S with M; main() { + var a; + a = new A(); + a = new A(); - - - - - - - - - - - - - - + a = new F(); } diff --git a/tests/language/mixin_legacy/type_parameters_errors_test.dart b/tests/language/mixin_legacy/type_parameters_errors_test.dart new file mode 100644 index 00000000000..fc694e15380 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_errors_test.dart @@ -0,0 +1,45 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +class S {} + +class M {} + +class A extends S with M {} + +class B extends S with M {} +// ^ +// [cfe] The type 'M' can't be mixed in. +// ^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.WRONG_NUMBER_OF_TYPE_ARGUMENTS +// [cfe] Expected 1 type arguments. +class C extends S with M {} +// ^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.WRONG_NUMBER_OF_TYPE_ARGUMENTS +// [cfe] Expected 1 type arguments. + +class F = S with M; +class G = S with M; +// ^ +// [cfe] The type 'M' can't be mixed in. +// ^^^^^^^^^^^^^^^^^ +// [analyzer] COMPILE_TIME_ERROR.WRONG_NUMBER_OF_TYPE_ARGUMENTS +// [cfe] Expected 1 type arguments. + +main() { + var a; + a = new A(); + a = new A(); + a = new A(); + // ^^^^^^^^^^^^^^^^^ + // [analyzer] COMPILE_TIME_ERROR.WRONG_NUMBER_OF_TYPE_ARGUMENTS + // [cfe] Expected 1 type arguments. + a = new F(); + a = new F(); + // ^^^^^^^^^^^^^^ + // [analyzer] COMPILE_TIME_ERROR.WRONG_NUMBER_OF_TYPE_ARGUMENTS + // [cfe] Expected 1 type arguments. +} diff --git a/tests/language/mixin_legacy/type_parameters_mixin_extends_test.dart b/tests/language/mixin_legacy/type_parameters_mixin_extends_test.dart new file mode 100644 index 00000000000..5ed3f81c58e --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_mixin_extends_test.dart @@ -0,0 +1,132 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M { + bool matches(o) { + bool isChecked = checkUsingIs(o); + if (checkedMode) { + Expect.equals(isChecked, checkUsingCheckedMode(o)); + } + return isChecked; + } + + bool checkUsingIs(o) { + return o is T; + } + + bool checkUsingCheckedMode(o) { + try { + T x = o; + } on Error { + return false; + } + return true; + } + + static final bool checkedMode = computeCheckedMode(); + static bool computeCheckedMode() { + try { + int x = "foo" as dynamic; + } on Error { + return true; + } + return false; + } +} + +class S {} + +class C0 extends S with M {} + +class C1 extends S with M {} + +class C2 extends S with M {} + +class C3 extends S with M {} + +main() { + var c0 = new C0(); + Expect.isTrue(c0 is M); + Expect.isFalse(c0 is M); + Expect.isFalse(c0 is M); + Expect.isTrue(c0.matches(c0)); + Expect.isTrue(c0.matches(42)); + Expect.isTrue(c0.matches("hello")); + + var c0_int = new C0(); + Expect.isTrue(c0_int is M); + Expect.isFalse(c0_int is M); + Expect.isFalse(c0_int is M); + Expect.isTrue(c0_int.matches(c0)); + Expect.isTrue(c0_int.matches(42)); + Expect.isTrue(c0_int.matches("hello")); + + var c0_String = new C0(); + Expect.isTrue(c0_String is M); + Expect.isFalse(c0_String is M); + Expect.isFalse(c0_String is M); + Expect.isTrue(c0_String.matches(c0)); + Expect.isTrue(c0_String.matches(42)); + Expect.isTrue(c0_String.matches("hello")); + + var c1 = new C1(); + Expect.isTrue(c1 is M); + Expect.isFalse(c1 is M); + Expect.isFalse(c1 is M); + Expect.isTrue(c1.matches(c1)); + Expect.isTrue(c1.matches(42)); + Expect.isTrue(c1.matches("hello")); + + var c1_int = new C1(); + Expect.isTrue(c1_int is M); + Expect.isTrue(c1_int is M); + Expect.isFalse(c1_int is M); + Expect.isFalse(c1_int.matches(c1)); + Expect.isTrue(c1_int.matches(42)); + Expect.isFalse(c1_int.matches("hello")); + + var c1_String = new C1(); + Expect.isTrue(c1_String is M); + Expect.isFalse(c1_String is M); + Expect.isTrue(c1_String is M); + Expect.isFalse(c1_String.matches(c1)); + Expect.isFalse(c1_String.matches(42)); + Expect.isTrue(c1_String.matches("hello")); + + var c2 = new C2(); + Expect.isTrue(c2 is M); + Expect.isTrue(c2 is M); + Expect.isFalse(c2 is M); + Expect.isFalse(c2.matches(c2)); + Expect.isTrue(c2.matches(42)); + Expect.isFalse(c2.matches("hello")); + + var c2_int = new C2(); + Expect.isTrue(c2_int is M); + Expect.isTrue(c2_int is M); + Expect.isFalse(c2_int is M); + Expect.isFalse(c2_int.matches(c2)); + Expect.isTrue(c2_int.matches(42)); + Expect.isFalse(c2_int.matches("hello")); + + var c2_String = new C2(); + Expect.isTrue(c2_String is M); + Expect.isTrue(c2_String is M); + Expect.isFalse(c2_String is M); + Expect.isFalse(c2_String.matches(c2)); + Expect.isTrue(c2_String.matches(42)); + Expect.isFalse(c2_String.matches("hello")); + + var c3 = new C3(); + Expect.isTrue(c3 is M); + Expect.isFalse(c3 is M); + Expect.isTrue(c3 is M); + Expect.isFalse(c3.matches(c2)); + Expect.isFalse(c3.matches(42)); + Expect.isTrue(c3.matches("hello")); +} diff --git a/tests/language/mixin_legacy/type_parameters_mixin_test.dart b/tests/language/mixin_legacy/type_parameters_mixin_test.dart new file mode 100644 index 00000000000..cd3a55846b9 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_mixin_test.dart @@ -0,0 +1,129 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class M { + bool matches(o) { + bool isChecked = checkUsingIs(o); + if (checkedMode) { + Expect.equals(isChecked, checkUsingCheckedMode(o)); + } + return isChecked; + } + + bool checkUsingIs(o) { + return o is T; + } + + bool checkUsingCheckedMode(o) { + try { + T x = o; + } on Error { + return false; + } + return true; + } + + static final bool checkedMode = computeCheckedMode(); + static bool computeCheckedMode() { + try { + int x = "foo" as dynamic; + } on Error { + return true; + } + return false; + } +} + +class S {} + +class C0 = S with M; +class C1 = S with M; +class C2 = S with M; +class C3 = S with M; + +main() { + var c0 = new C0(); + Expect.isTrue(c0 is M); + Expect.isFalse(c0 is M); + Expect.isFalse(c0 is M); + Expect.isTrue(c0.matches(c0)); + Expect.isTrue(c0.matches(42)); + Expect.isTrue(c0.matches("hello")); + + var c0_int = new C0(); + Expect.isTrue(c0_int is M); + Expect.isFalse(c0_int is M); + Expect.isFalse(c0_int is M); + Expect.isTrue(c0_int.matches(c0)); + Expect.isTrue(c0_int.matches(42)); + Expect.isTrue(c0_int.matches("hello")); + + var c0_String = new C0(); + Expect.isTrue(c0_String is M); + Expect.isFalse(c0_String is M); + Expect.isFalse(c0_String is M); + Expect.isTrue(c0_String.matches(c0)); + Expect.isTrue(c0_String.matches(42)); + Expect.isTrue(c0_String.matches("hello")); + + var c1 = new C1(); + Expect.isTrue(c1 is M); + Expect.isFalse(c1 is M); + Expect.isFalse(c1 is M); + Expect.isTrue(c1.matches(c1)); + Expect.isTrue(c1.matches(42)); + Expect.isTrue(c1.matches("hello")); + + var c1_int = new C1(); + Expect.isTrue(c1_int is M); + Expect.isTrue(c1_int is M); + Expect.isFalse(c1_int is M); + Expect.isFalse(c1_int.matches(c1)); + Expect.isTrue(c1_int.matches(42)); + Expect.isFalse(c1_int.matches("hello")); + + var c1_String = new C1(); + Expect.isTrue(c1_String is M); + Expect.isFalse(c1_String is M); + Expect.isTrue(c1_String is M); + Expect.isFalse(c1_String.matches(c1)); + Expect.isFalse(c1_String.matches(42)); + Expect.isTrue(c1_String.matches("hello")); + + var c2 = new C2(); + Expect.isTrue(c2 is M); + Expect.isTrue(c2 is M); + Expect.isFalse(c2 is M); + Expect.isFalse(c2.matches(c2)); + Expect.isTrue(c2.matches(42)); + Expect.isFalse(c2.matches("hello")); + + var c2_int = new C2(); + Expect.isTrue(c2_int is M); + Expect.isTrue(c2_int is M); + Expect.isFalse(c2_int is M); + Expect.isFalse(c2_int.matches(c2)); + Expect.isTrue(c2_int.matches(42)); + Expect.isFalse(c2_int.matches("hello")); + + var c2_String = new C2(); + Expect.isTrue(c2_String is M); + Expect.isTrue(c2_String is M); + Expect.isFalse(c2_String is M); + Expect.isFalse(c2_String.matches(c2)); + Expect.isTrue(c2_String.matches(42)); + Expect.isFalse(c2_String.matches("hello")); + + var c3 = new C3(); + Expect.isTrue(c3 is M); + Expect.isFalse(c3 is M); + Expect.isTrue(c3 is M); + Expect.isFalse(c3.matches(c2)); + Expect.isFalse(c3.matches(42)); + Expect.isTrue(c3.matches("hello")); +} diff --git a/tests/language/mixin_legacy/type_parameters_simple_test.dart b/tests/language/mixin_legacy/type_parameters_simple_test.dart new file mode 100644 index 00000000000..ac8d14316d1 --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_simple_test.dart @@ -0,0 +1,31 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S {} + +class M1 { + m1() => X; +} + +class M2 { + m2() => Y; +} + +class A extends S with M1, M2 {} + +main() { + var a = new A(); + // Getting "int" when calling toString() on the int type is not required. + // However, we want to keep the original names for the most common core types + // so we make sure to handle these specifically in the compiler. + Expect.equals("int", a.m1().toString()); + Expect.equals("int", a.m2().toString()); + var a2 = new A(); + Expect.equals("String", a2.m1().toString()); + Expect.equals("String", a2.m2().toString()); +} diff --git a/tests/language/mixin_legacy/type_parameters_super_extends_test.dart b/tests/language/mixin_legacy/type_parameters_super_extends_test.dart new file mode 100644 index 00000000000..8697a4d6d6d --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_super_extends_test.dart @@ -0,0 +1,132 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + bool matches(o) { + bool isChecked = checkUsingIs(o); + if (checkedMode) { + Expect.equals(isChecked, checkUsingCheckedMode(o)); + } + return isChecked; + } + + bool checkUsingIs(o) { + return o is T; + } + + bool checkUsingCheckedMode(o) { + try { + T x = o; + } on Error { + return false; + } + return true; + } + + static final bool checkedMode = computeCheckedMode(); + static bool computeCheckedMode() { + try { + int x = "foo" as dynamic; + } on Error { + return true; + } + return false; + } +} + +class M {} + +class C0 extends S with M {} + +class C1 extends S with M {} + +class C2 extends S with M {} + +class C3 extends S with M {} + +main() { + var c0 = new C0(); + Expect.isTrue(c0 is S); + Expect.isFalse(c0 is S); + Expect.isFalse(c0 is S); + Expect.isTrue(c0.matches(c0)); + Expect.isTrue(c0.matches(42)); + Expect.isTrue(c0.matches("hello")); + + var c0_int = new C0(); + Expect.isTrue(c0_int is S); + Expect.isFalse(c0_int is S); + Expect.isFalse(c0_int is S); + Expect.isTrue(c0_int.matches(c0)); + Expect.isTrue(c0_int.matches(42)); + Expect.isTrue(c0_int.matches("hello")); + + var c0_String = new C0(); + Expect.isTrue(c0_String is S); + Expect.isFalse(c0_String is S); + Expect.isFalse(c0_String is S); + Expect.isTrue(c0_String.matches(c0)); + Expect.isTrue(c0_String.matches(42)); + Expect.isTrue(c0_String.matches("hello")); + + var c1 = new C1(); + Expect.isTrue(c1 is S); + Expect.isFalse(c1 is S); + Expect.isFalse(c1 is S); + Expect.isTrue(c1.matches(c1)); + Expect.isTrue(c1.matches(42)); + Expect.isTrue(c1.matches("hello")); + + var c1_int = new C1(); + Expect.isTrue(c1_int is S); + Expect.isTrue(c1_int is S); + Expect.isFalse(c1_int is S); + Expect.isFalse(c1_int.matches(c1)); + Expect.isTrue(c1_int.matches(42)); + Expect.isFalse(c1_int.matches("hello")); + + var c1_String = new C1(); + Expect.isTrue(c1_String is S); + Expect.isFalse(c1_String is S); + Expect.isTrue(c1_String is S); + Expect.isFalse(c1_String.matches(c1)); + Expect.isFalse(c1_String.matches(42)); + Expect.isTrue(c1_String.matches("hello")); + + var c2 = new C2(); + Expect.isTrue(c2 is S); + Expect.isTrue(c2 is S); + Expect.isFalse(c2 is S); + Expect.isFalse(c2.matches(c2)); + Expect.isTrue(c2.matches(42)); + Expect.isFalse(c2.matches("hello")); + + var c2_int = new C2(); + Expect.isTrue(c2_int is S); + Expect.isTrue(c2_int is S); + Expect.isFalse(c2_int is S); + Expect.isFalse(c2_int.matches(c2)); + Expect.isTrue(c2_int.matches(42)); + Expect.isFalse(c2_int.matches("hello")); + + var c2_String = new C2(); + Expect.isTrue(c2_String is S); + Expect.isTrue(c2_String is S); + Expect.isFalse(c2_String is S); + Expect.isFalse(c2_String.matches(c2)); + Expect.isTrue(c2_String.matches(42)); + Expect.isFalse(c2_String.matches("hello")); + + var c3 = new C3(); + Expect.isTrue(c3 is S); + Expect.isFalse(c3 is S); + Expect.isTrue(c3 is S); + Expect.isFalse(c3.matches(c2)); + Expect.isFalse(c3.matches(42)); + Expect.isTrue(c3.matches("hello")); +} diff --git a/tests/language/mixin_legacy/type_parameters_super_test.dart b/tests/language/mixin_legacy/type_parameters_super_test.dart new file mode 100644 index 00000000000..4725ae59a6d --- /dev/null +++ b/tests/language/mixin_legacy/type_parameters_super_test.dart @@ -0,0 +1,100 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class S { + bool matches(o) => o is T; +} + +class M {} + +class C0 = S with M; +class C1 = S with M; +class C2 = S with M; +class C3 = S with M; + +main() { + var c0 = new C0(); + Expect.isTrue(c0 is S); + Expect.isFalse(c0 is S); + Expect.isFalse(c0 is S); + Expect.isTrue(c0.matches(c0)); + Expect.isTrue(c0.matches(42)); + Expect.isTrue(c0.matches("hello")); + + var c0_int = new C0(); + Expect.isTrue(c0_int is S); + Expect.isFalse(c0_int is S); + Expect.isFalse(c0_int is S); + Expect.isTrue(c0_int.matches(c0)); + Expect.isTrue(c0_int.matches(42)); + Expect.isTrue(c0_int.matches("hello")); + + var c0_String = new C0(); + Expect.isTrue(c0_String is S); + Expect.isFalse(c0_String is S); + Expect.isFalse(c0_String is S); + Expect.isTrue(c0_String.matches(c0)); + Expect.isTrue(c0_String.matches(42)); + Expect.isTrue(c0_String.matches("hello")); + + var c1 = new C1(); + Expect.isTrue(c1 is S); + Expect.isFalse(c1 is S); + Expect.isFalse(c1 is S); + Expect.isTrue(c1.matches(c1)); + Expect.isTrue(c1.matches(42)); + Expect.isTrue(c1.matches("hello")); + + var c1_int = new C1(); + Expect.isTrue(c1_int is S); + Expect.isTrue(c1_int is S); + Expect.isFalse(c1_int is S); + Expect.isFalse(c1_int.matches(c1)); + Expect.isTrue(c1_int.matches(42)); + Expect.isFalse(c1_int.matches("hello")); + + var c1_String = new C1(); + Expect.isTrue(c1_String is S); + Expect.isFalse(c1_String is S); + Expect.isTrue(c1_String is S); + Expect.isFalse(c1_String.matches(c1)); + Expect.isFalse(c1_String.matches(42)); + Expect.isTrue(c1_String.matches("hello")); + + var c2 = new C2(); + Expect.isTrue(c2 is S); + Expect.isTrue(c2 is S); + Expect.isFalse(c2 is S); + Expect.isFalse(c2.matches(c2)); + Expect.isTrue(c2.matches(42)); + Expect.isFalse(c2.matches("hello")); + + var c2_int = new C2(); + Expect.isTrue(c2_int is S); + Expect.isTrue(c2_int is S); + Expect.isFalse(c2_int is S); + Expect.isFalse(c2_int.matches(c2)); + Expect.isTrue(c2_int.matches(42)); + Expect.isFalse(c2_int.matches("hello")); + + var c2_String = new C2(); + Expect.isTrue(c2_String is S); + Expect.isTrue(c2_String is S); + Expect.isFalse(c2_String is S); + Expect.isFalse(c2_String.matches(c2)); + Expect.isTrue(c2_String.matches(42)); + Expect.isFalse(c2_String.matches("hello")); + + var c3 = new C3(); + Expect.isTrue(c3 is S); + Expect.isFalse(c3 is S); + Expect.isTrue(c3 is S); + Expect.isFalse(c3.matches(c2)); + Expect.isFalse(c3.matches(42)); + Expect.isTrue(c3.matches("hello")); +} diff --git a/tests/language/mixin_legacy/type_variable_test.dart b/tests/language/mixin_legacy/type_variable_test.dart new file mode 100644 index 00000000000..3971ec192b2 --- /dev/null +++ b/tests/language/mixin_legacy/type_variable_test.dart @@ -0,0 +1,34 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +// Regression test for generic mixin fields. + +class A { + T? field; +} + +class B = Object with A; + +class C extends B {} //# 03: ok +class D extends B {} //# 04: ok + +class E = Object with A; + +class F extends E {} //# 06: ok + +class G extends Object with A {} //# 07: ok +class H extends Object with A {} //# 08: ok + +void main() { + new A(); //# 01: ok + new B(); //# 02: ok + new C(); //# 03: continued + new D(); //# 04: continued + new E(); //# 05: ok + new F(); //# 06: continued + new G(); //# 07: continued + new H(); //# 08: continued +} diff --git a/tests/language/mixin_legacy/typedef_constructor_test.dart b/tests/language/mixin_legacy/typedef_constructor_test.dart new file mode 100644 index 00000000000..750b3e18bf7 --- /dev/null +++ b/tests/language/mixin_legacy/typedef_constructor_test.dart @@ -0,0 +1,24 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class A { + var field; + A(this.field); +} + +class Mixin { + var mixinField = 54; +} + +class MyClass = A with Mixin; + +main() { + var a = new MyClass(42); + Expect.equals(42, a.field); + Expect.equals(54, a.mixinField); +} diff --git a/tests/language/mixin_legacy/with_named_import_test.dart b/tests/language/mixin_legacy/with_named_import_test.dart new file mode 100644 index 00000000000..37a1575ccbf --- /dev/null +++ b/tests/language/mixin_legacy/with_named_import_test.dart @@ -0,0 +1,18 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import 'dart:collection' as collection; + +class Foo extends Object with collection.ListMixin { + int get length => 0; + operator [](int index) => null; + void operator []=(int index, value) => null; + set length(int newLength) => null; +} + +main() { + new Foo(); +} diff --git a/tests/language/mixin_legacy/with_two_implicit_constructors_test.dart b/tests/language/mixin_legacy/with_two_implicit_constructors_test.dart new file mode 100644 index 00000000000..cf872a2a514 --- /dev/null +++ b/tests/language/mixin_legacy/with_two_implicit_constructors_test.dart @@ -0,0 +1,22 @@ +// Copyright (c) 2023, 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. + +// @dart=2.19 + +import "package:expect/expect.dart"; + +class A { + var field; + A.bar() : field = 1; + A() : field = 2; +} + +class Mixin {} + +class B extends A with Mixin {} + +main() { + Expect.equals(2, new B().field); + new B.bar(); /*@compile-error=unspecified*/ +}