Files
sdk/pkg/vm/lib/transformations/pragma.dart
T
Alexander Markov 8924c18003 [vm/tests] Revert changes in pkg/vm unit tests after constant-update-2018 was disabled
Pkg/vm tests were adjusted after constant evaluation was enabled in the front-end.
As constant evaluation was reverted (4b7d256a06),
we also need to revert corresponding changes in pkg/vm unit tests.

Revert "[vm/bytecode] Update expectations for bytecode generator unit test"

This reverts commit 734c50cbf2.

Revert "[vm/aot/tfa] Update TFA tests after front-end starts evaluating constants"

This reverts commit 25cb45c02f.

Change-Id: I2fcc30571bec2dd904925724ddb7105567c7ecda
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/99782
Reviewed-by: Siva Annamalai <asiva@google.com>
Commit-Queue: Alexander Markov <alexmarkov@google.com>
2019-04-19 18:12:21 +00:00

109 lines
3.6 KiB
Dart

// Copyright (c) 2018, 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.
library vm.transformations.pragma;
import 'package:kernel/ast.dart';
import 'package:kernel/core_types.dart' show CoreTypes;
const kEntryPointPragmaName = "vm:entry-point";
const kExactResultTypePragmaName = "vm:exact-result-type";
const kNonNullableResultType = "vm:non-nullable-result-type";
abstract class ParsedPragma {}
enum PragmaEntryPointType { Default, GetterOnly, SetterOnly, CallOnly }
class ParsedEntryPointPragma extends ParsedPragma {
final PragmaEntryPointType type;
ParsedEntryPointPragma(this.type);
}
class ParsedResultTypeByTypePragma extends ParsedPragma {
final DartType type;
ParsedResultTypeByTypePragma(this.type);
}
class ParsedResultTypeByPathPragma extends ParsedPragma {
final String path;
ParsedResultTypeByPathPragma(this.path);
}
class ParsedNonNullableResultType extends ParsedPragma {
ParsedNonNullableResultType();
}
abstract class PragmaAnnotationParser {
/// May return 'null' if the annotation does not represent a recognized
/// @pragma.
ParsedPragma parsePragma(Expression annotation);
}
class ConstantPragmaAnnotationParser extends PragmaAnnotationParser {
final CoreTypes coreTypes;
ConstantPragmaAnnotationParser(this.coreTypes);
ParsedPragma parsePragma(Expression annotation) {
InstanceConstant pragmaConstant;
if (annotation is ConstantExpression) {
Constant constant = annotation.constant;
if (constant is InstanceConstant) {
if (constant.classReference.node == coreTypes.pragmaClass) {
pragmaConstant = constant;
}
}
}
if (pragmaConstant == null) return null;
String pragmaName;
Constant name = pragmaConstant.fieldValues[coreTypes.pragmaName.reference];
if (name is StringConstant) {
pragmaName = name.value;
} else {
return null;
}
Constant options =
pragmaConstant.fieldValues[coreTypes.pragmaOptions.reference];
assert(options != null);
switch (pragmaName) {
case kEntryPointPragmaName:
PragmaEntryPointType type;
if (options is NullConstant) {
type = PragmaEntryPointType.Default;
} else if (options is BoolConstant && options.value == true) {
type = PragmaEntryPointType.Default;
} else if (options is StringConstant) {
if (options.value == "get") {
type = PragmaEntryPointType.GetterOnly;
} else if (options.value == "set") {
type = PragmaEntryPointType.SetterOnly;
} else if (options.value == "call") {
type = PragmaEntryPointType.CallOnly;
} else {
throw "Error: string directive to @pragma('$kEntryPointPragmaName', ...) "
"must be either 'get' or 'set' for fields "
"or 'get' or 'call' for procedures.";
}
}
return type != null ? new ParsedEntryPointPragma(type) : null;
case kExactResultTypePragmaName:
if (options == null) return null;
if (options is TypeLiteralConstant) {
return new ParsedResultTypeByTypePragma(options.type);
} else if (options is StringConstant) {
return new ParsedResultTypeByPathPragma(options.value);
}
throw "ERROR: Unsupported option to '$kExactResultTypePragmaName' "
"pragma: $options";
case kNonNullableResultType:
return new ParsedNonNullableResultType();
default:
return null;
}
}
}