Skip to content

Commit

Permalink
[cfe] Add support for constants to Kernel text serialization
Browse files Browse the repository at this point in the history
The CL also finalizes the support for expressions because the constant
expressions can now be serialized.

Change-Id: I7bc98fc974d3be1d4b9f1712cf67f9fbe6496e01
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/153461
Reviewed-by: Johnni Winther <[email protected]>
Commit-Queue: Dmitry Stefantsov <[email protected]>
  • Loading branch information
Dmitry Stefantsov authored and [email protected] committed Jul 7, 2020
1 parent bec928c commit 2eee763
Show file tree
Hide file tree
Showing 5 changed files with 202 additions and 23 deletions.
3 changes: 3 additions & 0 deletions pkg/front_end/test/spell_checking_list_code.txt
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,7 @@ casing
cast
casted
casts
ce
cfe
ch
channel
Expand Down Expand Up @@ -495,6 +496,7 @@ human
i
i'll
i2b
ic
id
identifies
identifying
Expand Down Expand Up @@ -1138,6 +1140,7 @@ tuple2
tuple3
tuple4
tuple5
tuple6
type1
type2
typeref
Expand Down
1 change: 1 addition & 0 deletions pkg/front_end/test/spell_checking_list_common.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2701,6 +2701,7 @@ sink
sites
situation
situations
sixth
skip
skipped
skipping
Expand Down
51 changes: 51 additions & 0 deletions pkg/kernel/lib/text/serializer_combinators.dart
Original file line number Diff line number Diff line change
Expand Up @@ -466,6 +466,57 @@ class Tuple5<T1, T2, T3, T4, T5> {
const Tuple5(this.first, this.second, this.third, this.fourth, this.fifth);
}

class Tuple6Serializer<T1, T2, T3, T4, T5, T6>
extends TextSerializer<Tuple6<T1, T2, T3, T4, T5, T6>> {
final TextSerializer<T1> first;
final TextSerializer<T2> second;
final TextSerializer<T3> third;
final TextSerializer<T4> fourth;
final TextSerializer<T5> fifth;
final TextSerializer<T6> sixth;

const Tuple6Serializer(
this.first, this.second, this.third, this.fourth, this.fifth, this.sixth);

Tuple6<T1, T2, T3, T4, T5, T6> readFrom(
Iterator<Object> stream, DeserializationState state) {
return new Tuple6(
first.readFrom(stream, state),
second.readFrom(stream, state),
third.readFrom(stream, state),
fourth.readFrom(stream, state),
fifth.readFrom(stream, state),
sixth.readFrom(stream, state));
}

void writeTo(StringBuffer buffer, Tuple6<T1, T2, T3, T4, T5, T6> object,
SerializationState state) {
first.writeTo(buffer, object.first, state);
if (!second.isEmpty) buffer.write(' ');
second.writeTo(buffer, object.second, state);
if (!third.isEmpty) buffer.write(' ');
third.writeTo(buffer, object.third, state);
if (!fourth.isEmpty) buffer.write(' ');
fourth.writeTo(buffer, object.fourth, state);
if (!fifth.isEmpty) buffer.write(' ');
fifth.writeTo(buffer, object.fifth, state);
if (!sixth.isEmpty) buffer.write(' ');
sixth.writeTo(buffer, object.sixth, state);
}
}

class Tuple6<T1, T2, T3, T4, T5, T6> {
final T1 first;
final T2 second;
final T3 third;
final T4 fourth;
final T5 fifth;
final T6 sixth;

const Tuple6(
this.first, this.second, this.third, this.fourth, this.fifth, this.sixth);
}

// A serializer/deserializer for lists.
class ListSerializer<T> extends TextSerializer<List<T>> {
final TextSerializer<T> elements;
Expand Down
24 changes: 1 addition & 23 deletions pkg/kernel/lib/text/text_serialization_verifier.dart
Original file line number Diff line number Diff line change
Expand Up @@ -322,12 +322,6 @@ class VerificationState {
}
}

static bool isExpressionSupported(Expression node) =>
!isExpressionNotSupported(node);

static bool isExpressionNotSupported(Expression node) =>
node is InstanceCreation || node is ConstantExpression;

static bool isStatementSupported(Statement node) =>
!isStatementNotSupported(node);

Expand All @@ -343,46 +337,30 @@ class VerificationState {
static bool isSupported(Node node) => !isNotSupported(node);

static bool isNotSupported(Node node) =>
node is Expression && isExpressionNotSupported(node) ||
node is Statement && isStatementNotSupported(node) ||
node is FunctionNode && node.body == null ||
node is Procedure &&
(!node.isStatic || node.kind != ProcedureKind.Method) ||
node is AssertInitializer ||
node is BoolConstant ||
node is Catch ||
node is Class ||
node is Component ||
node is Constructor ||
node is DoubleConstant ||
node is Extension ||
node is Field ||
node is FieldInitializer ||
node is InstanceConstant ||
node is IntConstant ||
node is InvalidInitializer ||
node is Library ||
node is LibraryPart ||
node is ListConstant ||
node is LocalInitializer ||
node is MapConstant ||
node is MapEntry ||
node is Name && node.isPrivate ||
node is NullConstant ||
node is PartialInstantiationConstant ||
node is PrimitiveConstant ||
node is RedirectingFactoryConstructor ||
node is RedirectingInitializer ||
node is SetConstant ||
node is StringConstant ||
node is SuperInitializer ||
node is Supertype ||
node is SwitchCase ||
node is SymbolConstant ||
node is TearOffConstant ||
node is TypeLiteralConstant ||
node is Typedef ||
node is UnevaluatedConstant;
node is Typedef;
}

class TextSerializationVerifier extends RecursiveVisitor<void> {
Expand Down
146 changes: 146 additions & 0 deletions pkg/kernel/lib/text/text_serializer.dart
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,8 @@ class ExpressionTagger extends ExpressionVisitor<String>
String visitFileUriExpression(FileUriExpression _) => "with-uri";
String visitCheckLibraryIsLoaded(CheckLibraryIsLoaded _) => "is-loaded";
String visitLoadLibrary(LoadLibrary _) => "load";
String visitConstantExpression(ConstantExpression _) => "const";
String visitInstanceCreation(InstanceCreation _) => "object";
}

const TextSerializer<InvalidExpression> invalidExpressionSerializer =
Expand Down Expand Up @@ -740,6 +742,29 @@ TextSerializer<CheckLibraryIsLoaded> checkLibraryIsLoadedSerializer = Wrapped(
TextSerializer<LoadLibrary> loadLibrarySerializer = Wrapped(
(ll) => ll.import, (i) => LoadLibrary(i), libraryDependencySerializer);

TextSerializer<ConstantExpression> constantExpressionSerializer = Wrapped(
(ce) => Tuple2(ce.constant, ce.type),
(t) => ConstantExpression(t.first, t.second),
Tuple2Serializer(constantSerializer, dartTypeSerializer));

TextSerializer<InstanceCreation> instanceCreationSerializer = Wrapped(
(ic) => Tuple6(
ic.classReference.canonicalName,
ic.typeArguments,
ic.fieldValues.keys.map((r) => r.canonicalName).toList(),
ic.fieldValues.values.toList(),
ic.asserts,
ic.unusedArguments),
(t) => InstanceCreation(t.first.getReference(), t.second,
Map.fromIterables(t.third, t.fourth), t.fifth, t.sixth),
Tuple6Serializer(
CanonicalNameSerializer(),
ListSerializer(dartTypeSerializer),
ListSerializer(CanonicalNameSerializer()),
ListSerializer(expressionSerializer),
ListSerializer(assertStatementSerializer),
ListSerializer(expressionSerializer)));

Case<Expression> expressionSerializer =
new Case.uninitialized(const ExpressionTagger());

Expand Down Expand Up @@ -1605,6 +1630,109 @@ TextSerializer<LibraryDependency> libraryDependencySerializer = Wrapped(
DartInt(),
ListSerializer(expressionSerializer)));

class ConstantTagger extends ConstantVisitor<String>
implements Tagger<Constant> {
const ConstantTagger();

String tag(Constant node) => node.accept(this);

String visitBoolConstant(BoolConstant node) => "const-bool";
String visitDoubleConstant(DoubleConstant node) => "const-double";
String visitInstanceConstant(InstanceConstant node) => "const-object";
String visitIntConstant(IntConstant node) => "const-int";
String visitListConstant(ListConstant node) => "const-list";
String visitMapConstant(MapConstant node) => "const-map";
String visitNullConstant(NullConstant node) => "const-null";
String visitPartialInstantiationConstant(PartialInstantiationConstant node) =>
"const-apply";
String visitSetConstant(SetConstant node) => "const-set";
String visitStringConstant(StringConstant node) => "const-string";
String visitSymbolConstant(SymbolConstant node) => "const-symbol";
String visitTearOffConstant(TearOffConstant node) => "const-tearoff";
String visitTypeLiteralConstant(TypeLiteralConstant node) => "const-type";
String visitUnevaluatedConstant(UnevaluatedConstant node) => "const-expr";
}

TextSerializer<BoolConstant> boolConstantSerializer =
Wrapped((w) => w.value, (u) => BoolConstant(u), DartBool());

TextSerializer<DoubleConstant> doubleConstantSerializer =
Wrapped((w) => w.value, (u) => DoubleConstant(u), DartDouble());

TextSerializer<IntConstant> intConstantSerializer =
Wrapped((w) => w.value, (u) => IntConstant(u), DartInt());

TextSerializer<ListConstant> listConstantSerializer = Wrapped(
(w) => Tuple2(w.typeArgument, w.entries),
(u) => ListConstant(u.first, u.second),
Tuple2Serializer(dartTypeSerializer, ListSerializer(constantSerializer)));

TextSerializer<MapConstant> mapConstantSerializer = Wrapped(
(w) => Tuple3(w.keyType, w.valueType, w.entries),
(u) => MapConstant(u.first, u.second, u.third),
Tuple3Serializer(
dartTypeSerializer,
dartTypeSerializer,
Zip(
Tuple2Serializer(ListSerializer(constantSerializer),
ListSerializer(constantSerializer)),
(k, v) => ConstantMapEntry(k, v),
(z) => Tuple2(z.key, z.value))));

TextSerializer<NullConstant> nullConstantSerializer =
Wrapped((w) => null, (u) => NullConstant(), Nothing());

TextSerializer<PartialInstantiationConstant>
partialInstantiationConstantSerializer = Wrapped(
(w) => Tuple2(w.tearOffConstant, w.types),
(u) => PartialInstantiationConstant(u.first, u.second),
Tuple2Serializer(
tearOffConstantSerializer, ListSerializer(dartTypeSerializer)));

TextSerializer<SetConstant> setConstantSerializer = Wrapped(
(w) => Tuple2(w.typeArgument, w.entries),
(u) => SetConstant(u.first, u.second),
Tuple2Serializer(dartTypeSerializer, ListSerializer(constantSerializer)));

TextSerializer<StringConstant> stringConstantSerializer =
Wrapped((w) => w.value, (u) => StringConstant(u), DartString());

TextSerializer<SymbolConstant> symbolConstantSerializer = Wrapped(
(w) => Tuple2(w.name, w.libraryReference?.canonicalName),
(u) => SymbolConstant(u.first, u.second?.getReference()),
Tuple2Serializer(DartString(), Optional(CanonicalNameSerializer())));

TextSerializer<TearOffConstant> tearOffConstantSerializer = Wrapped(
(w) => w.procedureReference.canonicalName,
(u) => TearOffConstant.byReference(u.getReference()),
CanonicalNameSerializer());

TextSerializer<TypeLiteralConstant> typeLiteralConstantSerializer =
Wrapped((w) => w.type, (u) => TypeLiteralConstant(u), dartTypeSerializer);

TextSerializer<UnevaluatedConstant> unevaluatedConstantSerializer = Wrapped(
(w) => w.expression, (u) => UnevaluatedConstant(u), expressionSerializer);

TextSerializer<InstanceConstant> instanceConstantSerializer =
Wrapped<
Tuple4<CanonicalName, List<DartType>, List<CanonicalName>,
List<Constant>>,
InstanceConstant>(
(w) => Tuple4(
w.classReference.canonicalName,
w.typeArguments,
w.fieldValues.keys.map((r) => r.canonicalName).toList(),
w.fieldValues.values.toList()),
(u) => InstanceConstant(u.first.getReference(), u.second,
Map.fromIterables(u.third.map((c) => c.getReference()), u.fourth)),
Tuple4Serializer(
CanonicalNameSerializer(),
ListSerializer(dartTypeSerializer),
ListSerializer(CanonicalNameSerializer()),
ListSerializer(constantSerializer)));

Case<Constant> constantSerializer = Case.uninitialized(ConstantTagger());

void initializeSerializers() {
expressionSerializer.registerTags({
"string": stringLiteralSerializer,
Expand Down Expand Up @@ -1660,6 +1788,8 @@ void initializeSerializers() {
"with-uri": fileUriExpressionSerializer,
"is-loaded": checkLibraryIsLoadedSerializer,
"load": loadLibrarySerializer,
"const": constantExpressionSerializer,
"object": instanceCreationSerializer,
});
dartTypeSerializer.registerTags({
"invalid": invalidTypeSerializer,
Expand Down Expand Up @@ -1705,4 +1835,20 @@ void initializeSerializers() {
"legacy": libraryContentsSerializer,
"null-safe": libraryContentsSerializer,
});
constantSerializer.registerTags({
"const-bool": boolConstantSerializer,
"const-double": doubleConstantSerializer,
"const-int": intConstantSerializer,
"const-list": listConstantSerializer,
"const-map": mapConstantSerializer,
"const-null": nullConstantSerializer,
"const-apply": partialInstantiationConstantSerializer,
"const-set": setConstantSerializer,
"const-string": stringConstantSerializer,
"const-symbol": symbolConstantSerializer,
"const-tearoff": tearOffConstantSerializer,
"const-type": typeLiteralConstantSerializer,
"const-expr": unevaluatedConstantSerializer,
"const-object": instanceConstantSerializer,
});
}

0 comments on commit 2eee763

Please sign in to comment.