76548a7ab9
In dart2wasm applications are by default deployed in `-O2` mode which implies `--minify`. Given this is the default configuration for customers, we want good testing of this configuration and not large numbers of approved failures. => Rewrite various tests to not depend on `<obj>.runtimeType.toString()` Change-Id: I1108b28c63b8bec6ad94df0d7b878b3339776df9 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/436281 Reviewed-by: Lasse Nielsen <lrn@google.com> Commit-Queue: Martin Kustermann <kustermann@google.com>
171 lines
6.9 KiB
Dart
171 lines
6.9 KiB
Dart
// 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.
|
|
|
|
/// Behavior variations of the current Dart execution.
|
|
///
|
|
/// Dart compilers vary the behavior of the compiled code in certain predictable
|
|
/// ways depending on the target platform or optimization flags, for example.
|
|
///
|
|
/// When writing SDK or language tests, the tests should be aware of, and
|
|
/// account for, those variations.
|
|
///
|
|
/// The properties in this library are used to narrow expectations in SDK tests.
|
|
/// That helps preserve test coverage in the presence of behavior variations in
|
|
/// Dart implementations and testing configurations.
|
|
///
|
|
/// Some variations in behavior are language compliant:
|
|
///
|
|
/// * [number semantics][1] change when targeting JavaScript
|
|
/// * some features have modalities (whether assertions are enabled, weak vs
|
|
/// sound null safety),
|
|
/// * some compilers support a subset of SDK libraries (for example, `dart:io`
|
|
/// on native platforms), and
|
|
/// * some behaviors are purposely unspecified (such as string representation
|
|
/// of types, which can change in the presence of minification
|
|
/// optimizations).
|
|
///
|
|
/// Some variations can result from unsafe optimizations. These are deviations
|
|
/// from the language or library contracts. Typically, this is done by backends
|
|
/// like dart2js or dart2wasm that run on a sandboxed environment which limits
|
|
/// the consequences of an erroneous optimization. Examples include:
|
|
///
|
|
/// * omitting covariant and dynamic parameter checks
|
|
/// * omitting implicit or explicit downcasts
|
|
/// * bypassing checks in library code, like range checks when accessing
|
|
/// native arrays in JavaScript.
|
|
///
|
|
/// Regardless of the reason, variations are deliberate and should be accounted
|
|
/// for in testing. Each behavior in this library is based on an underlying
|
|
/// variation in an existing Dart implementation.
|
|
///
|
|
/// Note: A coarse-grain alternative for each of these is also available in the
|
|
/// `test_runner` infrastructure for narrowing expectations on entire test
|
|
/// files.
|
|
///
|
|
/// [1]: https://dart.dev/guides/language/numbers "Numbers in Dart"
|
|
// TODO(54798): include conditions for VM/AOT/Wasm backends (current
|
|
// definitions only reflect variations under dart2js and DDC compilers).
|
|
// TODO(54798): update this dartdoc to also have a link to the standard
|
|
// reference of variations when it becomes available in the SDK wiki.
|
|
library;
|
|
|
|
import 'config.dart';
|
|
|
|
/// Whether `assert`s are enabled.
|
|
// TODO: If information can be made available as a constant, use that.
|
|
// (For example if we introduce a compilation-environment entry for it.)
|
|
final bool enabledAsserts = (() {
|
|
bool result = false;
|
|
assert(result = true);
|
|
return result;
|
|
})();
|
|
|
|
/// Whether the program is running without sound null safety.
|
|
const bool unsoundNullSafety = <Null>[] is List<Object>;
|
|
|
|
/// Whether the program is running with JavaScript [number semantics][1].
|
|
///
|
|
/// In code compiled to JavaScript, Dart integers are represented by JavaScript
|
|
/// numbers, which have different ranges and behavior than native integers.
|
|
///
|
|
/// For example, using JavaScript numbers, an `int` value like `1` also
|
|
/// implements `double` and is the same object as `1.0`. In native numbers,
|
|
/// those values are two different objects, and integers do not implement
|
|
/// `double`.
|
|
///
|
|
/// _Note: We do not use the term web-numbers because the Dart Wasm backend is
|
|
/// considered a web backend, but uses native number semantics._
|
|
///
|
|
/// [1]: https://dart.dev/guides/language/numbers "Numbers in Dart"
|
|
const bool jsNumbers = identical(1, 1.0);
|
|
|
|
/// Whether [Type.toString] exposes the source names of types.
|
|
///
|
|
/// If so, the strings are readable and can be used to match certain
|
|
/// expectations. Typically this is not the case in production configurations
|
|
/// that enable minification, like `dart compile js -O2` and `dart compile exe`.
|
|
bool get readableTypeStrings =>
|
|
!const bool.fromEnvironment('dart.tool.dart2js.minify') &&
|
|
!const bool.fromEnvironment('dart.tool.dart2wasm.minify') &&
|
|
!(isVmConfiguration && configAsString.contains('obfuscate'));
|
|
|
|
/// Whether [Symbol]s were minified.
|
|
///
|
|
/// If [Symbol]s are minified, rruntime allocated `Symbol` objects
|
|
/// will not compare equal to const `Symbols` (e.g., `new Symbol('x') != #x`).
|
|
bool get minifiedSymbols =>
|
|
const bool.fromEnvironment('dart.tool.dart2wasm.minify');
|
|
|
|
/// Whether specific subtypes of [Error] with details are thrown or generic
|
|
/// [Error]s.
|
|
bool get preciseErrorsWithDetails =>
|
|
!const bool.fromEnvironment('dart.tool.dart2wasm.minify');
|
|
|
|
/// Whether thrown [Error] objects will have a [StackTrace] attached.
|
|
bool get errorsHaveStackTrace =>
|
|
!const bool.fromEnvironment('dart.tool.dart2wasm.minify');
|
|
|
|
/// Whether runtime parameter type checks are enforced.
|
|
///
|
|
/// Runtime parameter type checks include both covariant parameter checks,
|
|
/// either from generics or declared as `covariant`, and parameter checks of
|
|
/// dynamic function invocations through `dynamic` or `Function`.
|
|
///
|
|
/// For example, this code should fail a covariant parameter check:
|
|
///
|
|
/// ```dart
|
|
/// List<Object> list = <String>[];
|
|
/// list.add(1);
|
|
/// ```
|
|
///
|
|
/// And this code should fail a dynamic invocation parameter type check:
|
|
///
|
|
/// ```dart
|
|
/// class A {
|
|
/// m(int x) {}
|
|
/// }
|
|
/// (A() as dynamic).m("value");
|
|
/// ```
|
|
bool get checkedParameters =>
|
|
!const bool.fromEnvironment('dart.tool.dart2js.types:trust');
|
|
|
|
/// Whether implicit downcasts from `dynamic` are typed checked at runtime.
|
|
///
|
|
/// The language allows an expression of type `dynamic` to be used
|
|
/// where any other type is required, by doing a runtime check that
|
|
/// the value has the required type.
|
|
/// This value is `false` when that runtime check is omitted.
|
|
///
|
|
/// For example, this code should fail with an invalid implicit cast:
|
|
/// ```dart
|
|
/// dynamic d = 3; String s = d;
|
|
/// ```
|
|
bool get checkedImplicitDowncasts =>
|
|
!const bool.fromEnvironment('dart.tool.dart2js.types:trust');
|
|
|
|
/// Whether RTI optimizations are disabled at compile time.
|
|
///
|
|
/// This can cause some type errors to present differently than they otherwise
|
|
/// would. For example, when these optimizations are disabled ArgumentErrors may
|
|
/// present as TypeErrors instead.
|
|
bool get rtiOptimizationsDisabled =>
|
|
const bool.fromEnvironment('dart.tool.dart2js.disable_rti_optimization',
|
|
defaultValue: true);
|
|
|
|
/// Whether explicit casts are type checked at runtime.
|
|
///
|
|
/// An expression like `e as String` should perform a runtime check that the
|
|
/// value of `e` implements `String`.
|
|
/// This value is `false` when that runtime check is omitted, and the runtime
|
|
/// code will just use the value of `e` assuming it to be a string.
|
|
///
|
|
/// For example, this code should fail the explicit cast when the integer `3` is
|
|
/// checked for being a `String`:
|
|
///
|
|
/// ```dart
|
|
/// Object o = 3;
|
|
/// o as String;
|
|
/// ```
|
|
bool get checkedExplicitCasts => true;
|