blob: 002bb31f526a49cde9cdc84514a9981706e8e8c4 [file] [log] [blame]
// Copyright (c) 2025, 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.
part of '../../ast.dart';
/// Generalized notion of a variable.
sealed class Variable extends TreeNode {
VariableContext get context => parent as VariableContext;
// CaptureKind get captureKind => context.captureKind;
/// The cosmetic name of the variable from the source code, if exists.
String? get cosmeticName;
@override
void toTextInternal(AstPrinter printer) {
printer.write(printer.getVariableName(this));
}
}
/// The root of the sealed hierarchy of non-type variables.
sealed class ExpressionVariable extends Variable {}
/// Local variables. They aren't Statements. A [LocalVariable] is "declared" in
/// the [VariableContext] it appears in. [VariableInitialization]
/// (which is a [Statement]) marks the spot of the original variable declaration
/// in the Dart program.
class LocalVariable extends ExpressionVariable {
@override
String? cosmeticName;
LocalVariable({this.cosmeticName});
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "LocalVariable(${toStringInternal()})";
}
}
/// Abstract parameter class, the parent for positional and named parameters.
sealed class FunctionParameter extends ExpressionVariable {}
/// Positional parameters. The [cosmeticName] field is optional and doesn't
/// affect the runtime semantics of the program.
class PositionalParameter extends FunctionParameter {
@override
final String? cosmeticName;
PositionalParameter(this.cosmeticName);
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "PositionalParameter(${toStringInternal()})";
}
}
/// Named parameters. The [name] field is mandatory.
class NamedParameter extends FunctionParameter {
final String name;
@override
String get cosmeticName => name;
NamedParameter({required this.name});
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "NamedParameter(${toStringInternal()})";
}
}
/// The variable storage for `this`.
class ThisVariable extends ExpressionVariable {
@override
String get cosmeticName => "this";
ThisVariable();
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "ThisVariable(${toStringInternal()})";
}
}
/// A variable introduced during desugaring. Such variables don't correspond to
/// any variable declared by the programmer.
class SyntheticVariable extends ExpressionVariable {
@override
String? cosmeticName;
SyntheticVariable({this.cosmeticName});
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "SyntheticVariable(${toStringInternal()})";
}
}
/// The enum reflecting the kind of a variable context. A context is
/// [assertCaptured] if it contains the variables captured in a closure within
/// an `assert` and not captured anywhere outside of `assert`s.
enum CaptureKind {
notCaptured,
captured,
assertCaptured;
}
/// The box storing some of the variables in the scope it's associated with. It
/// serves as the "declaration" of the variables it contains for the runtime
/// environments.
class VariableContext extends TreeNode {
final CaptureKind captureKind;
final List<Variable> variables;
VariableContext({required this.captureKind, required this.variables});
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "VariableContext(${toStringInternal()})";
}
@override
void toTextInternal(AstPrinter printer) {
printer.write('[');
for (int index = 0; index < variables.length; index++) {
if (index > 0) {
printer.write(', ');
}
variables[index].toTextInternal(printer);
}
printer.write(']');
}
}
/// The collection of the contexts pertaining to a scope-inducing node. The
/// [Scopes] are supposed to be treated as the points of declaration of the
/// variables they contain. They aren't [Statement]s, but a runtime may choose
/// to interpret the [Scope] in an executable way before any [Statement]s or
/// [Expression]s of its node.
class Scope extends TreeNode {
final List<VariableContext> contexts;
Scope(this.contexts);
@override
R accept<R>(TreeVisitor<R> v) {
// TODO(cstefantsova): Implement accept.
throw UnimplementedError();
}
@override
R accept1<R, A>(TreeVisitor1<R, A> v, A arg) {
// TODO(cstefantsova): Implement accept1.
throw UnimplementedError();
}
@override
void transformChildren(Transformer v) {
// TODO(cstefantsova): Implement transformChildren.
}
@override
void transformOrRemoveChildren(RemovingTransformer v) {
// TODO(cstefantsova): Implement transformOrRemoveChildren.
}
@override
void visitChildren(Visitor v) {
// TODO(cstefantsova): Implement visitChildren.
}
@override
String toString() {
return "Scope(${toStringInternal()})";
}
@override
void toTextInternal(AstPrinter printer) {
printer.write('[');
for (int index = 0; index < contexts.length; index++) {
if (index > 0) {
printer.write(', ');
}
contexts[index].toTextInternal(printer);
}
printer.write(']');
}
}
/// The root of the sealed hierarchy of the nodes that provide a scope, such as
/// loops, functions, and blocks.
sealed class ScopeProvider {
/// The scope of the [ScopeProvider].
///
/// It's represented as nullable due to the experimental status of the
/// feature. When the feature isn't enabled, [scope] should return null.
Scope? get scope;
}