From 1c6752905ecaa93f2c41507580ba480ad94d06e9 Mon Sep 17 00:00:00 2001 From: "Sergey G. Grekhov" Date: Fri, 26 Jan 2024 15:24:28 +0200 Subject: [PATCH] #2485. Add is T constant evaluation tests (#2501) Add `is T` constant evaluation tests --- .../Constants/as_type_A01_t02.dart | 8 +- .../Constants/as_type_A02_t01.dart | 4 + .../Constants/as_type_A02_t02.dart | 4 - .../Constants/is_type_A01_t01.dart | 76 ++++++++++++ .../Constants/is_type_A01_t02.dart | 97 +++++++++++++++ .../Constants/is_type_A01_t03.dart | 52 +++++++++ .../Constants/is_type_A02_t01.dart | 110 ++++++++++++++++++ .../Constants/is_type_A02_t02.dart | 46 ++++++++ .../Constants/is_type_A03_t01.dart | 55 +++++++++ .../Expressions/Type_Cast/syntax_t07.dart | 5 + 10 files changed, 450 insertions(+), 7 deletions(-) create mode 100644 Language/Expressions/Constants/is_type_A01_t01.dart create mode 100644 Language/Expressions/Constants/is_type_A01_t02.dart create mode 100644 Language/Expressions/Constants/is_type_A01_t03.dart create mode 100644 Language/Expressions/Constants/is_type_A02_t01.dart create mode 100644 Language/Expressions/Constants/is_type_A02_t02.dart create mode 100644 Language/Expressions/Constants/is_type_A03_t01.dart diff --git a/Language/Expressions/Constants/as_type_A01_t02.dart b/Language/Expressions/Constants/as_type_A01_t02.dart index 0b069e9105..5202602e9b 100644 --- a/Language/Expressions/Constants/as_type_A01_t02.dart +++ b/Language/Expressions/Constants/as_type_A01_t02.dart @@ -52,7 +52,7 @@ typedef IntET1Alias = IntET1; typedef IntET2Alias = IntET2; void foo() {} - +void as() {} int bar(T t) => 42; main() { @@ -73,7 +73,8 @@ main() { const fo7 = IntET2(1) as FutureOr; const f1 = foo as void Function(); - const f2 = bar as int Function(int); + const f2 = as as void Function(); + const f3 = bar as int Function(int); const d = 2 as dynamic; @@ -86,6 +87,7 @@ main() { Expect.identical(fo4, fo5); Expect.identical(fo6, fo7); Expect.identical(foo, f1); - Expect.identical(bar, f2); + Expect.identical(as, f2); + Expect.identical(bar, f3); Expect.identical(2, d); } diff --git a/Language/Expressions/Constants/as_type_A02_t01.dart b/Language/Expressions/Constants/as_type_A02_t01.dart index 30fb172980..89d726fb93 100644 --- a/Language/Expressions/Constants/as_type_A02_t01.dart +++ b/Language/Expressions/Constants/as_type_A02_t01.dart @@ -106,5 +106,9 @@ main() { const c19 = c as Object; // ^ // [analyzer] unspecified +// [cfe] unspecified + const c20 = () {} as Function; +// ^^^^^ +// [analyzer] unspecified // [cfe] unspecified } diff --git a/Language/Expressions/Constants/as_type_A02_t02.dart b/Language/Expressions/Constants/as_type_A02_t02.dart index 11c9b96b2b..fc6f862778 100644 --- a/Language/Expressions/Constants/as_type_A02_t02.dart +++ b/Language/Expressions/Constants/as_type_A02_t02.dart @@ -28,10 +28,6 @@ main() { const cIntExtension = IntExtension as Type; // ^^^^^^^^^^^^ // [analyzer] unspecified -// [cfe] unspecified - const F = () {} as Function; -// ^^^^^ -// [analyzer] unspecified // [cfe] unspecified const R1 = (void,) as Type; // ^^^^ diff --git a/Language/Expressions/Constants/is_type_A01_t01.dart b/Language/Expressions/Constants/is_type_A01_t01.dart new file mode 100644 index 0000000000..7c0ce62d23 --- /dev/null +++ b/Language/Expressions/Constants/is_type_A01_t01.dart @@ -0,0 +1,76 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// +/// @description Checks that an expression of the form `e is T` is a constant +/// expression if `e` is a constant expression and `T` is a constant type +/// expression +/// @author sgrekhov22@gmail.com +/// @issue 54620 + +// SharedOptions=--enable-experiment=inline-class + +import "../../../Utils/expect.dart"; + +class C { + const C(); +} + +extension type const IntET1(int _) {} +extension type const IntET2(int _) implements int {} + +main() { + const c1 = 1 is num; + const c2 = (3.14 as num) is double; + const c3 = IntET1(1) is int; + const c4 = IntET2(1) is int; + const c5 = (IntET1(1),) is (int,); + const c6 = (IntET2(1),) is (int,); + const c7 = [IntET1(1)] is List; + const c8 = [IntET2(1)] is List; + const c9 = {IntET1(1)} is Set; + const c10 = {IntET2(1)} is Set; + const c11 = {IntET1(1): IntET1(2)} is Map; + const c12 = {IntET1(1): IntET2(2)} is Map; + const c13 = {IntET2(1): IntET1(2)} is Map; + const c14 = {IntET2(1): IntET2(2)} is Map; + const c15 = 1 is IntET1; + const c16 = 1 is IntET2; + const c17 = IntET1(1) is IntET2; + const c18 = IntET2(1) is IntET1; + const c19 = C() is Object; + const c20 = const C() is Object; + const c21 = () is (); + const c22 = (i: 1) is ({num i}); + + Expect.isTrue(c1); + Expect.isTrue(c2); + Expect.isTrue(c3); + Expect.isTrue(c4); + Expect.isTrue(c5); + Expect.isTrue(c6); + Expect.isTrue(c7); + Expect.isTrue(c8); + Expect.isTrue(c9); + Expect.isTrue(c10); + Expect.isTrue(c11); + Expect.isTrue(c12); + Expect.isTrue(c13); + Expect.isTrue(c14); + Expect.isTrue(c15); + Expect.isTrue(c16); + Expect.isTrue(c17); + Expect.isTrue(c18); + Expect.isTrue(c19); + Expect.isTrue(c20); + Expect.isTrue(c21); + Expect.isTrue(c22); +} diff --git a/Language/Expressions/Constants/is_type_A01_t02.dart b/Language/Expressions/Constants/is_type_A01_t02.dart new file mode 100644 index 0000000000..9477accc65 --- /dev/null +++ b/Language/Expressions/Constants/is_type_A01_t02.dart @@ -0,0 +1,97 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// ... +/// A constant type expression is one of: +/// • An simple or qualified identifier denoting a type declaration (a type +/// alias, class or mixin declaration) that is not qualified by a deferred +/// prefix, optionally followed by type arguments of the form +/// where T1, ..., Tn are constant type expressions. +/// • A type of the form FutureOr where T is a constant type expression. +/// • A function type R Function(argumentTypes) (where +/// R and may be omitted) and where R, typeParameters +/// and argumentTypes (if present) contain only constant type expressions. +/// • The type void. +/// • The type dynamic +/// +/// @description Checks that an expression of the form `e is T` is a constant +/// expression if `e` is a constant expression and `T` is a constant type +/// expression. Test different constant type expressions +/// @author sgrekhov22@gmail.com +/// @issue 54636 + +// SharedOptions=--enable-experiment=inline-class + +import "dart:async"; +import "../../../Utils/expect.dart"; + +mixin M {} + +class C with M { + const C(); +} + +typedef CNumAlias = C; + +enum E { + e1, e2; +} + +extension type const IntET1(int _) {} +extension type const IntET2(int _) implements int {} + +typedef IntET1Alias = IntET1; +typedef IntET2Alias = IntET2; + +void foo() {} +void as() {} +int bar(T t) => 42; + +main() { + const c1 = C() is C; + const c2 = C() is M; + const c3 = E.e1 is E; + const c4 = C() is C; + const c5 = C() is CNumAlias; + const c6 = IntET1(1) is IntET2Alias; + const c7 = IntET2(1) is IntET1Alias; + + const fo1 = C() is FutureOr; + const fo2 = C() is FutureOr; + const fo3 = E.e1 is FutureOr; + const fo4 = C() is FutureOr>; + const fo5 = C() is FutureOr; + const fo6 = IntET1(1) is FutureOr; + const fo7 = IntET2(1) is FutureOr; + + const f1 = foo is void Function(); + const f2 = bar is int Function(int); + + const d = 2 is dynamic; + + Expect.isTrue(c1); + Expect.isTrue(c2); + Expect.isTrue(c3); + Expect.isTrue(c4); + Expect.isTrue(c5); + Expect.isTrue(c6); + Expect.isTrue(c7); + Expect.isTrue(fo1); + Expect.isTrue(fo2); + Expect.isTrue(fo3); + Expect.isTrue(fo4); + Expect.isTrue(fo5); + Expect.isTrue(fo6); + Expect.isTrue(fo7); + Expect.isTrue(f1); + Expect.isTrue(f2); + Expect.isTrue(d); +} diff --git a/Language/Expressions/Constants/is_type_A01_t03.dart b/Language/Expressions/Constants/is_type_A01_t03.dart new file mode 100644 index 0000000000..d6767d8e09 --- /dev/null +++ b/Language/Expressions/Constants/is_type_A01_t03.dart @@ -0,0 +1,52 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// ... +/// A constant type expression is one of: +/// • An simple or qualified identifier denoting a type declaration (a type +/// alias, class or mixin declaration) that is not qualified by a deferred +/// prefix, optionally followed by type arguments of the form +/// where T1, ..., Tn are constant type expressions. +/// • A type of the form FutureOr where T is a constant type expression. +/// • A function type R Function(argumentTypes) (where +/// R and may be omitted) and where R, typeParameters +/// and argumentTypes (if present) contain only constant type expressions. +/// • The type void. +/// • The type dynamic +/// +/// @description Checks that an expression of the form `e is T` is a constant +/// expression if `T` is a constant type expression of type `FutureOr` or +/// an extension type with a representation type `void` +/// @author sgrekhov22@gmail.com +/// @issue 54620 + +// SharedOptions=--enable-experiment=inline-class + +import "dart:async"; +import "../../../Utils/expect.dart"; + +extension type const VoidET(void _) {} + +main() { + const c1 = 1 is VoidET; + const c2 = 2 is FutureOr; + const c3 = (3,) is (VoidET,); + const c4 = (4,) is (FutureOr,); + const c5 = (i: 5) is ({VoidET i}); + const c6 = (i: 6) is ({FutureOr i}); + + Expect.isTrue(c1); + Expect.isTrue(c2); + Expect.isTrue(c3); + Expect.isTrue(c4); + Expect.isTrue(c5); + Expect.isTrue(c6); +} diff --git a/Language/Expressions/Constants/is_type_A02_t01.dart b/Language/Expressions/Constants/is_type_A02_t01.dart new file mode 100644 index 0000000000..dfc3f14856 --- /dev/null +++ b/Language/Expressions/Constants/is_type_A02_t01.dart @@ -0,0 +1,110 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// +/// @description Checks that an expression of the form `e is T` is not a +/// constant expression if `e` is not a constant expression +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=inline-class + +class C { + C(); +} + +extension type IntET1(int _) {} +extension type IntET2(int _) implements int {} + +test() { + const c = T is Type; +// ^ +// [analyzer] unspecified +// [cfe] unspecified +} + +main() { + int i = 1; + var d = 3.14; + var c = C(); + + const c1 = i is num; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + const c2 = (d as num) is double; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + const c3 = IntET1(1) is int; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c4 = IntET2(1) is int; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c5 = (i,) is (int,); +// ^ +// [analyzer] unspecified +// [cfe] unspecified + const c6 = (IntET1(1),) is (int,); +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c7 = (IntET2(1),) is (int,); +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c8 = [i] is List; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + const c9 = [IntET1(1)] is List; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c10 = [IntET2(1)] is List; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c11 = {d} is Set; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + const c12 = {IntET1(1)} is Set; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c13 = {IntET2(1)} is Set; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c14 = {IntET1(1): IntET1(2)} is Map; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c15 = {IntET2(1): IntET2(2)} is Map; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c16 = IntET1(1) is IntET2; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c17 = IntET2(1) is IntET1; +// ^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const c19 = c is Object; +// ^ +// [analyzer] unspecified +// [cfe] unspecified +} diff --git a/Language/Expressions/Constants/is_type_A02_t02.dart b/Language/Expressions/Constants/is_type_A02_t02.dart new file mode 100644 index 0000000000..16e29fb85c --- /dev/null +++ b/Language/Expressions/Constants/is_type_A02_t02.dart @@ -0,0 +1,46 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// +/// @description Checks that an expression of the form `e is T` is not a +/// constant expression if `e` is not an expression +/// @author sgrekhov22@gmail.com + +extension IntExtension on int {} + +main() { + const Foo = int Function() is Function; +// ^^^^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const Void = void is Type; +// ^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const cIntExtension = IntExtension is Type; +// ^^^^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const F = () {} is Function; +// ^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const R1 = (void,) is Type; +// ^^^^ +// [analyzer] unspecified +// [cfe] unspecified + const R2 = ({int i}) is Record; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + + +} diff --git a/Language/Expressions/Constants/is_type_A03_t01.dart b/Language/Expressions/Constants/is_type_A03_t01.dart new file mode 100644 index 0000000000..b632d52210 --- /dev/null +++ b/Language/Expressions/Constants/is_type_A03_t01.dart @@ -0,0 +1,55 @@ +// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A constant expression is an expression whose value can never +/// change, and that can be evaluated entirely at compile time. +/// A constant expression is one of the following: +/// ... +/// • An expression of the form e is T is potentially constant if e is a +/// potentially constant expression and T is a constant type expression, and +/// it is further constant if e is constant. +/// ... +/// A constant type expression is one of: +/// • An simple or qualified identifier denoting a type declaration (a type +/// alias, class or mixin declaration) that is not qualified by a deferred +/// prefix, optionally followed by type arguments of the form +/// where T1, ..., Tn are constant type expressions. +/// • A type of the form FutureOr where T is a constant type expression. +/// • A function type R Function(argumentTypes) (where +/// R and may be omitted) and where R, typeParameters +/// and argumentTypes (if present) contain only constant type expressions. +/// • The type void. +/// • The type dynamic +/// +/// @description Checks that an expression of the form `e is T` is not a +/// constant expression if `T` is not a constant type expression +/// @author sgrekhov22@gmail.com + +import "constants_lib.dart" deferred as p; + +extension IntExtension on int {} + +main() { + const Num = num; + + const c1 = 1 is Num; +// ^^^ +// [analyzer] unspecified +// [cfe] unspecified + + const c2 = 1 is p.A; +// ^^^ +// [analyzer] unspecified +// [cfe] unspecified + + const c3 = 1 is IntExtension; +// ^^^^^^^^^^^^ +// [analyzer] unspecified +// [cfe] unspecified + + const c4 = 1 is 42; +// ^^ +// [analyzer] unspecified +// [cfe] unspecified +} diff --git a/Language/Expressions/Type_Cast/syntax_t07.dart b/Language/Expressions/Type_Cast/syntax_t07.dart index 7b132afe59..eb2ca63ad0 100644 --- a/Language/Expressions/Type_Cast/syntax_t07.dart +++ b/Language/Expressions/Type_Cast/syntax_t07.dart @@ -14,5 +14,10 @@ main() { var v1 = 1 as void; // ^^^^ // [analyzer] unspecified +// [cfe] unspecified + + const c = 1 as void; +// ^^^^ +// [analyzer] unspecified // [cfe] unspecified }