Extract module 'deserialization' out of 'serialization'

'deserialization' stays in core because it's needed both in compiler and
reflection, but 'serialization' is used only in the compiler
This commit is contained in:
Alexander Udalov
2015-03-27 04:24:32 +03:00
parent d09e0e73fa
commit 32c3bb8c7f
60 changed files with 203 additions and 188 deletions
+15
View File
@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="JAVA_MODULE" version="4">
<component name="NewModuleRootManager" inherit-compiler-output="true">
<exclude-output />
<content url="file://$MODULE_DIR$">
<sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
</content>
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
<orderEntry type="library" exported="" name="protobuf-java" level="project" />
<orderEntry type="library" name="javax.inject" level="project" />
<orderEntry type="module" module-name="descriptors" exported="" />
<orderEntry type="module" module-name="util.runtime" />
</component>
</module>
+40
View File
@@ -0,0 +1,40 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.builtins;
import "core/deserialization/src/descriptors.proto";
option java_outer_classname = "BuiltInsProtoBuf";
option optimize_for = LITE_RUNTIME;
extend Package {
// id in StringTable
repeated int32 class_name = 150 [packed = true];
}
extend Class {
repeated Annotation class_annotation = 150;
}
extend Callable {
repeated Annotation callable_annotation = 150;
optional Annotation.Argument.Value compile_time_value = 151;
}
extend Callable.ValueParameter {
repeated Annotation parameter_annotation = 150;
}
+298
View File
@@ -0,0 +1,298 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization;
option java_outer_classname = "ProtoBuf";
option optimize_for = LITE_RUNTIME; // Smaller runtime
option java_generic_services = false; // Less code
message StringTable {
repeated string string = 1;
}
message QualifiedNameTable {
message QualifiedName {
optional int32 parent_qualified_name = 1 [default = -1];
// Id in the StringTable
required int32 short_name = 2;
optional Kind kind = 3 [default = PACKAGE];
enum Kind {
CLASS = 0;
PACKAGE = 1;
LOCAL = 2;
}
}
repeated QualifiedName qualified_name = 1;
}
message Annotation {
message Argument {
message Value {
enum Type {
BYTE = 0;
CHAR = 1;
SHORT = 2;
INT = 3;
LONG = 4;
FLOAT = 5;
DOUBLE = 6;
BOOLEAN = 7;
STRING = 8;
CLASS = 9;
ENUM = 10;
ANNOTATION = 11;
ARRAY = 12;
}
// Note: a *Value* has a Type, not an Argument! This is done for future language features which may involve using arrays
// of elements of different types. Such entries are allowed in the constant pool of JVM class files.
// However, to save space, this field is optional: in case of homogeneous arrays, only the type of the first element is required
optional Type type = 1;
// Only one of the following values should be present. Consider using `oneof` instead when we upgrade to protobuf 2.6.0+
optional sint64 int_value = 2;
optional float float_value = 3;
optional double double_value = 4;
// id in StringTable
optional int32 string_value = 5;
// If type = CLASS, FQ name id of the referenced class; if type = ENUM, FQ name id of the enum class
optional int32 class_id = 6;
// id in StringTable
optional int32 enum_value_id = 7;
optional Annotation annotation = 8;
repeated Value array_element = 9;
}
// id in StringTable
required int32 name_id = 1;
required Value value = 2;
}
// Class FQ name id
required int32 id = 1;
repeated Argument argument = 2;
}
message Type {
message Constructor {
enum Kind {
CLASS = 0;
TYPE_PARAMETER = 1;
}
optional Kind kind = 1 [default = CLASS];
required int32 id = 2; // CLASS - fqName id, TYPE_PARAMETER - type parameter id
}
required Constructor constructor = 1;
message Argument {
enum Projection {
IN = 0;
OUT = 1;
INV = 2;
STAR = 3;
}
optional Projection projection = 1 [default = INV];
optional Type type = 2; // when projection is STAR, no type is written, otherwise type must be specified
}
repeated Argument argument = 2;
optional bool nullable = 3 [default = false];
// Id in the StringTable
// If this field is set, the type is flexible.
// All the fields above represent its lower bound, and flexible_upper_bound must be set and represents its upper bound.
optional int32 flexible_type_capabilities_id = 4;
// While such an "indirect" encoding helps backwards compatibility with pre-flexible-types versions of this format,
// we use it mainly to save space: having a special mandatory tag on each an every type just to have an option
// to represent flexible types is too many wasted bytes.
optional Type flexible_upper_bound = 5;
}
message TypeParameter {
required int32 id = 1;
// Id in the StringTable
required int32 name = 2;
optional bool reified = 3 [default = false];
enum Variance {
IN = 0;
OUT = 1;
INV = 2;
}
optional Variance variance = 4 [default = INV];
repeated Type upper_bound = 5;
}
message Class {
enum Kind {
// 3 bits
CLASS = 0;
TRAIT = 1;
ENUM_CLASS = 2;
ENUM_ENTRY = 3;
ANNOTATION_CLASS = 4;
OBJECT = 5;
CLASS_OBJECT = 6;
}
/*
Visibility
Modality
has_annotation
ClassKind
is_inner
*/
optional int32 flags = 1 [default = 0 /*internal final class, no annotations*/];
required int32 fq_name = 3;
// If this field is present, it contains the name of companion object.
optional int32 companion_object_name = 4;
repeated TypeParameter type_parameter = 5;
repeated Type supertype = 6;
// we store only names, because the actual information must reside in the corresponding .class files,
// to be obtainable through reflection at runtime
repeated int32 nested_class_name = 7;
repeated Callable member = 11;
repeated int32 enum_entry = 12;
message PrimaryConstructor {
// If this field is present, it contains serialized data for the primary constructor.
// Otherwise it's default and can be created manually upon deserialization
optional Callable data = 1;
}
// This field is present if and only if the class has a primary constructor
optional PrimaryConstructor primary_constructor = 13;
repeated Callable secondary_constructor = 14;
extensions 100 to 199;
}
message Package {
repeated Callable member = 1;
extensions 100 to 199;
}
message Callable {
enum MemberKind {
// 2 bits
DECLARATION = 0;
FAKE_OVERRIDE = 1;
DELEGATION = 2;
SYNTHESIZED = 3;
}
enum CallableKind {
// 2 bits
FUN = 0;
VAL = 1;
VAR = 2;
CONSTRUCTOR = 3;
}
/*
Visibility
Modality
has_annotations
CallableKind
MemberKind
hasGetter
hasSetter
hasConstant
*/
optional int32 flags = 1;
/*
isNotDefault
Visibility
Modality
has_annotations
*/
optional int32 getter_flags = 9 /* absent => same as property */;
optional int32 setter_flags = 10 /* absent => same as property */;
repeated TypeParameter type_parameter = 4;
optional Type receiver_type = 5;
// Id in the StringTable
required int32 name = 6;
message ValueParameter {
/*
declaresDefault
has_annotations
*/
optional int32 flags = 1;
// Id in the StringTable
required int32 name = 2;
required Type type = 3;
optional Type vararg_element_type = 4;
extensions 100 to 199;
}
// Value parameters for functions and constructors, or setter value parameter for properties
repeated ValueParameter value_parameter = 7;
required Type return_type = 8;
extensions 100 to 199;
}
enum Modality {
// 2 bits
FINAL = 0x00;
OPEN = 0x01;
ABSTRACT = 0x02;
}
enum Visibility {
// 3 bits
INTERNAL = 0x00;
PRIVATE = 0x01;
PROTECTED = 0x02;
PUBLIC = 0x03;
PRIVATE_TO_THIS = 0x04;
LOCAL = 0x05;
}
@@ -0,0 +1,58 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization;
import com.google.protobuf.ExtensionRegistryLite;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.serialization.deserialization.NameResolver;
import org.jetbrains.kotlin.utils.UtilsPackage;
import java.io.ByteArrayInputStream;
import java.io.IOException;
public final class ClassData {
@NotNull
public static ClassData read(@NotNull byte[] bytes, @NotNull ExtensionRegistryLite registry) {
try {
ByteArrayInputStream in = new ByteArrayInputStream(bytes);
NameResolver nameResolver = NameResolver.read(in);
ProtoBuf.Class classProto = ProtoBuf.Class.parseFrom(in, registry);
return new ClassData(nameResolver, classProto);
}
catch (IOException e) {
throw UtilsPackage.rethrow(e);
}
}
private final NameResolver nameResolver;
private final ProtoBuf.Class classProto;
public ClassData(@NotNull NameResolver nameResolver, @NotNull ProtoBuf.Class classProto) {
this.nameResolver = nameResolver;
this.classProto = classProto;
}
@NotNull
public NameResolver getNameResolver() {
return nameResolver;
}
@NotNull
public ProtoBuf.Class getClassProto() {
return classProto;
}
}
@@ -0,0 +1,273 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization;
import com.google.protobuf.Internal;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.descriptors.*;
public class Flags {
private Flags() {}
// Common
public static final FlagField<Boolean> HAS_ANNOTATIONS = FlagField.booleanFirst();
public static final FlagField<ProtoBuf.Visibility> VISIBILITY = FlagField.after(HAS_ANNOTATIONS, ProtoBuf.Visibility.values());
public static final FlagField<ProtoBuf.Modality> MODALITY = FlagField.after(VISIBILITY, ProtoBuf.Modality.values());
// Class
public static final FlagField<ProtoBuf.Class.Kind> CLASS_KIND = FlagField.after(MODALITY, ProtoBuf.Class.Kind.values());
public static final FlagField<Boolean> INNER = FlagField.booleanAfter(CLASS_KIND);
// Callables
public static final FlagField<ProtoBuf.Callable.CallableKind> CALLABLE_KIND = FlagField.after(MODALITY,
ProtoBuf.Callable.CallableKind.values());
public static final FlagField<ProtoBuf.Callable.MemberKind> MEMBER_KIND = FlagField.after(CALLABLE_KIND,
ProtoBuf.Callable.MemberKind.values());
public static final FlagField<Boolean> HAS_GETTER = FlagField.booleanAfter(MEMBER_KIND);
public static final FlagField<Boolean> HAS_SETTER = FlagField.booleanAfter(HAS_GETTER);
public static final FlagField<Boolean> HAS_CONSTANT = FlagField.booleanAfter(HAS_SETTER);
// Parameters
public static final FlagField<Boolean> DECLARES_DEFAULT_VALUE = FlagField.booleanAfter(HAS_ANNOTATIONS);
// Accessors
// It's important that this flag is negated: "is NOT default" instead of "is default"
public static final FlagField<Boolean> IS_NOT_DEFAULT = FlagField.booleanAfter(MODALITY);
// ---
private static <E> int bitWidth(@NotNull E[] enumEntries) {
int length = enumEntries.length - 1;
if (length == 0) return 1;
for (int i = 31; i >= 0; i--) {
if ((length & (1 << i)) != 0) return i + 1;
}
throw new IllegalStateException("Empty enum: " + enumEntries.getClass());
}
public static int getClassFlags(
boolean hasAnnotations,
Visibility visibility,
Modality modality,
ClassKind kind,
boolean inner,
boolean isCompanionObject
) {
return HAS_ANNOTATIONS.toFlags(hasAnnotations)
| MODALITY.toFlags(modality(modality))
| VISIBILITY.toFlags(visibility(visibility))
| CLASS_KIND.toFlags(classKind(kind, isCompanionObject))
| INNER.toFlags(inner)
;
}
private static ProtoBuf.Class.Kind classKind(ClassKind kind, boolean isCompanionObject) {
if (isCompanionObject) return ProtoBuf.Class.Kind.CLASS_OBJECT;
switch (kind) {
case CLASS:
return ProtoBuf.Class.Kind.CLASS;
case TRAIT:
return ProtoBuf.Class.Kind.TRAIT;
case ENUM_CLASS:
return ProtoBuf.Class.Kind.ENUM_CLASS;
case ENUM_ENTRY:
return ProtoBuf.Class.Kind.ENUM_ENTRY;
case ANNOTATION_CLASS:
return ProtoBuf.Class.Kind.ANNOTATION_CLASS;
case OBJECT:
return ProtoBuf.Class.Kind.OBJECT;
}
throw new IllegalArgumentException("Unknown class kind: " + kind);
}
public static int getCallableFlags(
boolean hasAnnotations,
@NotNull Visibility visibility,
@NotNull Modality modality,
@NotNull CallableMemberDescriptor.Kind memberKind,
@NotNull ProtoBuf.Callable.CallableKind callableKind,
boolean hasGetter,
boolean hasSetter,
boolean hasConstant
) {
return HAS_ANNOTATIONS.toFlags(hasAnnotations)
| MODALITY.toFlags(modality(modality))
| VISIBILITY.toFlags(visibility(visibility))
| MEMBER_KIND.toFlags(memberKind(memberKind))
| CALLABLE_KIND.toFlags(callableKind)
| HAS_GETTER.toFlags(hasGetter)
| HAS_SETTER.toFlags(hasSetter)
| HAS_CONSTANT.toFlags(hasConstant)
;
}
public static int getAccessorFlags(
boolean hasAnnotations,
@NotNull Visibility visibility,
@NotNull Modality modality,
boolean isNotDefault
) {
return HAS_ANNOTATIONS.toFlags(hasAnnotations)
| MODALITY.toFlags(modality(modality))
| VISIBILITY.toFlags(visibility(visibility))
| IS_NOT_DEFAULT.toFlags(isNotDefault)
;
}
@NotNull
private static ProtoBuf.Visibility visibility(@NotNull Visibility visibility) {
if (visibility == Visibilities.INTERNAL) {
return ProtoBuf.Visibility.INTERNAL;
}
else if (visibility == Visibilities.PUBLIC) {
return ProtoBuf.Visibility.PUBLIC;
}
else if (visibility == Visibilities.PRIVATE) {
return ProtoBuf.Visibility.PRIVATE;
}
else if (visibility == Visibilities.PRIVATE_TO_THIS) {
return ProtoBuf.Visibility.PRIVATE_TO_THIS;
}
else if (visibility == Visibilities.PROTECTED) {
return ProtoBuf.Visibility.PROTECTED;
}
else if (visibility == Visibilities.LOCAL) {
return ProtoBuf.Visibility.LOCAL;
}
throw new IllegalArgumentException("Unknown visibility: " + visibility);
}
@NotNull
private static ProtoBuf.Modality modality(@NotNull Modality modality) {
switch (modality) {
case FINAL:
return ProtoBuf.Modality.FINAL;
case OPEN:
return ProtoBuf.Modality.OPEN;
case ABSTRACT:
return ProtoBuf.Modality.ABSTRACT;
}
throw new IllegalArgumentException("Unknown modality: " + modality);
}
@NotNull
private static ProtoBuf.Callable.MemberKind memberKind(@NotNull CallableMemberDescriptor.Kind kind) {
switch (kind) {
case DECLARATION:
return ProtoBuf.Callable.MemberKind.DECLARATION;
case FAKE_OVERRIDE:
return ProtoBuf.Callable.MemberKind.FAKE_OVERRIDE;
case DELEGATION:
return ProtoBuf.Callable.MemberKind.DELEGATION;
case SYNTHESIZED:
return ProtoBuf.Callable.MemberKind.SYNTHESIZED;
}
throw new IllegalArgumentException("Unknown member kind: " + kind);
}
public static int getValueParameterFlags(boolean hasAnnotations, boolean declaresDefaultValue) {
return HAS_ANNOTATIONS.toFlags(hasAnnotations)
| DECLARES_DEFAULT_VALUE.toFlags(declaresDefaultValue)
;
}
// Infrastructure
public static abstract class FlagField<E> {
public static <E extends Internal.EnumLite> FlagField<E> after(FlagField<?> previousField, E[] values) {
int offset = previousField.offset + previousField.bitWidth;
return new EnumLiteFlagField<E>(offset, values);
}
public static <E extends Internal.EnumLite> FlagField<E> first(E[] values) {
return new EnumLiteFlagField<E>(0, values);
}
public static FlagField<Boolean> booleanFirst() {
return new BooleanFlagField(0);
}
public static FlagField<Boolean> booleanAfter(FlagField<?> previousField) {
int offset = previousField.offset + previousField.bitWidth;
return new BooleanFlagField(offset);
}
private final int offset;
private final int bitWidth;
private final E[] values;
private FlagField(int offset, E[] values) {
this.offset = offset;
this.bitWidth = bitWidth(values);
this.values = values;
}
public E get(int flags) {
int maskUnshifted = (1 << bitWidth) - 1;
int mask = maskUnshifted << offset;
int value = (flags & mask) >> offset;
for (E e : values) {
if (getIntValue(e) == value) {
return e;
}
}
throw new IllegalStateException("Flag not found: " + value);
}
public int toFlags(E value) {
return getIntValue(value) << offset;
}
protected abstract int getIntValue(E value);
}
private static class BooleanFlagField extends FlagField<Boolean> {
private static final Boolean[] BOOLEAN = { false, true };
public BooleanFlagField(int offset) {
super(offset, BOOLEAN);
}
@Override
protected int getIntValue(Boolean value) {
return value ? 1 : 0;
}
}
private static class EnumLiteFlagField<E extends Internal.EnumLite> extends FlagField<E> {
public EnumLiteFlagField(int offset, E[] values) {
super(offset, values);
}
@Override
protected int getIntValue(E value) {
return value.getNumber();
}
}
}
@@ -0,0 +1,58 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization;
import com.google.protobuf.ExtensionRegistryLite;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.serialization.deserialization.NameResolver;
import org.jetbrains.kotlin.utils.UtilsPackage;
import java.io.ByteArrayInputStream;
import java.io.IOException;
public final class PackageData {
@NotNull
public static PackageData read(@NotNull byte[] bytes, @NotNull ExtensionRegistryLite registry) {
try {
ByteArrayInputStream in = new ByteArrayInputStream(bytes);
NameResolver nameResolver = NameResolver.read(in);
ProtoBuf.Package packageProto = ProtoBuf.Package.parseFrom(in, registry);
return new PackageData(nameResolver, packageProto);
}
catch (IOException e) {
throw UtilsPackage.rethrow(e);
}
}
private final NameResolver nameResolver;
private final ProtoBuf.Package packageProto;
public PackageData(@NotNull NameResolver nameResolver, @NotNull ProtoBuf.Package packageProto) {
this.nameResolver = nameResolver;
this.packageProto = packageProto;
}
@NotNull
public NameResolver getNameResolver() {
return nameResolver;
}
@NotNull
public ProtoBuf.Package getPackageProto() {
return packageProto;
}
}
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,96 @@
// Generated by the protocol buffer compiler. DO NOT EDIT!
// source: core/deserialization/src/builtins.proto
package org.jetbrains.kotlin.serialization.builtins;
public final class BuiltInsProtoBuf {
private BuiltInsProtoBuf() {}
public static void registerAllExtensions(
com.google.protobuf.ExtensionRegistryLite registry) {
registry.add(org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf.className);
registry.add(org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf.classAnnotation);
registry.add(org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf.callableAnnotation);
registry.add(org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf.compileTimeValue);
registry.add(org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf.parameterAnnotation);
}
public static final int CLASS_NAME_FIELD_NUMBER = 150;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Package { ... }</code>
*/
public static final
com.google.protobuf.GeneratedMessageLite.GeneratedExtension<
org.jetbrains.kotlin.serialization.ProtoBuf.Package,
java.util.List<java.lang.Integer>> className = com.google.protobuf.GeneratedMessageLite
.newRepeatedGeneratedExtension(
org.jetbrains.kotlin.serialization.ProtoBuf.Package.getDefaultInstance(),
null,
null,
150,
com.google.protobuf.WireFormat.FieldType.INT32,
true);
public static final int CLASS_ANNOTATION_FIELD_NUMBER = 150;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Class { ... }</code>
*/
public static final
com.google.protobuf.GeneratedMessageLite.GeneratedExtension<
org.jetbrains.kotlin.serialization.ProtoBuf.Class,
java.util.List<org.jetbrains.kotlin.serialization.ProtoBuf.Annotation>> classAnnotation = com.google.protobuf.GeneratedMessageLite
.newRepeatedGeneratedExtension(
org.jetbrains.kotlin.serialization.ProtoBuf.Class.getDefaultInstance(),
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.getDefaultInstance(),
null,
150,
com.google.protobuf.WireFormat.FieldType.MESSAGE,
false);
public static final int CALLABLE_ANNOTATION_FIELD_NUMBER = 150;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Callable { ... }</code>
*/
public static final
com.google.protobuf.GeneratedMessageLite.GeneratedExtension<
org.jetbrains.kotlin.serialization.ProtoBuf.Callable,
java.util.List<org.jetbrains.kotlin.serialization.ProtoBuf.Annotation>> callableAnnotation = com.google.protobuf.GeneratedMessageLite
.newRepeatedGeneratedExtension(
org.jetbrains.kotlin.serialization.ProtoBuf.Callable.getDefaultInstance(),
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.getDefaultInstance(),
null,
150,
com.google.protobuf.WireFormat.FieldType.MESSAGE,
false);
public static final int COMPILE_TIME_VALUE_FIELD_NUMBER = 151;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Callable { ... }</code>
*/
public static final
com.google.protobuf.GeneratedMessageLite.GeneratedExtension<
org.jetbrains.kotlin.serialization.ProtoBuf.Callable,
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument.Value> compileTimeValue = com.google.protobuf.GeneratedMessageLite
.newSingularGeneratedExtension(
org.jetbrains.kotlin.serialization.ProtoBuf.Callable.getDefaultInstance(),
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument.Value.getDefaultInstance(),
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument.Value.getDefaultInstance(),
null,
151,
com.google.protobuf.WireFormat.FieldType.MESSAGE);
public static final int PARAMETER_ANNOTATION_FIELD_NUMBER = 150;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Callable.ValueParameter { ... }</code>
*/
public static final
com.google.protobuf.GeneratedMessageLite.GeneratedExtension<
org.jetbrains.kotlin.serialization.ProtoBuf.Callable.ValueParameter,
java.util.List<org.jetbrains.kotlin.serialization.ProtoBuf.Annotation>> parameterAnnotation = com.google.protobuf.GeneratedMessageLite
.newRepeatedGeneratedExtension(
org.jetbrains.kotlin.serialization.ProtoBuf.Callable.ValueParameter.getDefaultInstance(),
org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.getDefaultInstance(),
null,
150,
com.google.protobuf.WireFormat.FieldType.MESSAGE,
false);
static {
}
// @@protoc_insertion_point(outer_class_scope)
}
@@ -0,0 +1,24 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization;
public enum AnnotatedCallableKind {
FUNCTION,
PROPERTY,
PROPERTY_GETTER,
PROPERTY_SETTER
}
@@ -0,0 +1,57 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.serialization.ProtoBuf;
import org.jetbrains.kotlin.types.JetType;
import java.util.List;
public interface AnnotationAndConstantLoader<A, C> {
@NotNull
List<A> loadClassAnnotations(
@NotNull ProtoBuf.Class classProto,
@NotNull NameResolver nameResolver
);
@NotNull
List<A> loadCallableAnnotations(
@NotNull ProtoContainer container,
@NotNull ProtoBuf.Callable proto,
@NotNull NameResolver nameResolver,
@NotNull AnnotatedCallableKind kind
);
@NotNull
List<A> loadValueParameterAnnotations(
@NotNull ProtoContainer container,
@NotNull ProtoBuf.Callable callable,
@NotNull NameResolver nameResolver,
@NotNull AnnotatedCallableKind kind,
@NotNull ProtoBuf.Callable.ValueParameter proto
);
@Nullable
C loadPropertyConstant(
@NotNull ProtoContainer container,
@NotNull ProtoBuf.Callable proto,
@NotNull NameResolver nameResolver,
@NotNull JetType expectedType
);
}
@@ -0,0 +1,166 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptorImpl
import org.jetbrains.kotlin.descriptors.ValueParameterDescriptor
import org.jetbrains.kotlin.serialization.ProtoBuf.Annotation
import org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument
import org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument.Value
import org.jetbrains.kotlin.serialization.ProtoBuf.Annotation.Argument.Value.Type
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.constants.*
import org.jetbrains.kotlin.types.JetType
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.types.ErrorUtils
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.types.Variance
import org.jetbrains.kotlin.types.typeUtil.isSubtypeOf
public class AnnotationDeserializer(private val module: ModuleDescriptor) {
private val builtIns: KotlinBuiltIns
get() = module.builtIns
public fun deserializeAnnotation(proto: Annotation, nameResolver: NameResolver): AnnotationDescriptor {
val annotationClass = resolveClass(nameResolver.getClassId(proto.getId()))
val arguments = if (proto.getArgumentCount() == 0 || ErrorUtils.isError(annotationClass)) {
mapOf()
}
else {
val parameterByName = annotationClass.getConstructors().single().getValueParameters().toMap { it.getName() }
val arguments = proto.getArgumentList().map { resolveArgument(it, parameterByName, nameResolver) }.filterNotNull()
arguments.toMap()
}
return AnnotationDescriptorImpl(annotationClass.getDefaultType(), arguments)
}
private fun resolveArgument(
proto: Argument,
parameterByName: Map<Name, ValueParameterDescriptor>,
nameResolver: NameResolver
): Pair<ValueParameterDescriptor, CompileTimeConstant<*>>? {
val parameter = parameterByName[nameResolver.getName(proto.getNameId())] ?: return null
return Pair(parameter, resolveValue(parameter.getType(), proto.getValue(), nameResolver))
}
public fun resolveValue(
expectedType: JetType,
value: Value,
nameResolver: NameResolver
): CompileTimeConstant<*> {
val result = when (value.getType()) {
Type.BYTE -> ByteValue(value.getIntValue().toByte(), true, true, true)
Type.CHAR -> CharValue(value.getIntValue().toChar(), true, true, true)
Type.SHORT -> ShortValue(value.getIntValue().toShort(), true, true, true)
Type.INT -> IntValue(value.getIntValue().toInt(), true, true, true)
Type.LONG -> LongValue(value.getIntValue(), true, true, true)
Type.FLOAT -> FloatValue(value.getFloatValue(), true, true)
Type.DOUBLE -> DoubleValue(value.getDoubleValue(), true, true)
Type.BOOLEAN -> BooleanValue(value.getIntValue() != 0L, true, true)
Type.STRING -> {
StringValue(nameResolver.getString(value.getStringValue()), true, true)
}
Type.CLASS -> {
// TODO: support class literals
error("Class literal annotation arguments are not supported yet (${nameResolver.getClassId(value.getClassId())})")
}
Type.ENUM -> {
resolveEnumValue(nameResolver.getClassId(value.getClassId()), nameResolver.getName(value.getEnumValueId()))
}
Type.ANNOTATION -> {
AnnotationValue(deserializeAnnotation(value.getAnnotation(), nameResolver))
}
Type.ARRAY -> {
val expectedIsArray = KotlinBuiltIns.isArray(expectedType) || KotlinBuiltIns.isPrimitiveArray(expectedType)
val arrayElements = value.getArrayElementList()
val actualArrayType =
if (arrayElements.isNotEmpty()) {
val actualElementType = resolveArrayElementType(arrayElements.first(), nameResolver)
builtIns.getPrimitiveArrayJetTypeByPrimitiveJetType(actualElementType) ?:
builtIns.getArrayType(Variance.INVARIANT, actualElementType)
}
else {
// In the case of empty array, no element has the element type, so we fall back to the expected type, if any.
// This is not very accurate when annotation class has been changed without recompiling clients,
// but should not in fact matter because the value is empty anyway
if (expectedIsArray) expectedType else builtIns.getArrayType(Variance.INVARIANT, builtIns.getAnyType())
}
val expectedElementType = builtIns.getArrayElementType(if (expectedIsArray) expectedType else actualArrayType)
ArrayValue(
arrayElements.map { resolveValue(expectedElementType, it, nameResolver) },
actualArrayType,
true, true
)
}
else -> error("Unsupported annotation argument type: ${value.getType()} (expected $expectedType)")
}
if (result.getType(builtIns) isSubtypeOf expectedType) {
return result
}
else {
// This means that an annotation class has been changed incompatibly without recompiling clients
return ErrorValue.create("Unexpected argument value")
}
}
// NOTE: see analogous code in BinaryClassAnnotationAndConstantLoaderImpl
private fun resolveEnumValue(enumClassId: ClassId, enumEntryName: Name): CompileTimeConstant<*> {
val enumClass = resolveClass(enumClassId)
if (enumClass.getKind() == ClassKind.ENUM_CLASS) {
val enumEntry = enumClass.getUnsubstitutedInnerClassesScope().getClassifier(enumEntryName)
if (enumEntry is ClassDescriptor) {
return EnumValue(enumEntry, true)
}
}
return ErrorValue.create("Unresolved enum entry: $enumClassId.$enumEntryName")
}
private fun resolveArrayElementType(value: Value, nameResolver: NameResolver): JetType =
with(builtIns) {
when (value.getType()) {
Type.BYTE -> getByteType()
Type.CHAR -> getCharType()
Type.SHORT -> getShortType()
Type.INT -> getIntType()
Type.LONG -> getLongType()
Type.FLOAT -> getFloatType()
Type.DOUBLE -> getDoubleType()
Type.BOOLEAN -> getBooleanType()
Type.STRING -> getStringType()
Type.CLASS -> error("Arrays of class literals are not supported yet") // TODO: support arrays of class literals
Type.ENUM -> resolveClass(nameResolver.getClassId(value.getClassId())).getDefaultType()
Type.ANNOTATION -> resolveClass(nameResolver.getClassId(value.getAnnotation().getId())).getDefaultType()
Type.ARRAY -> error("Array of arrays is impossible")
else -> error("Unknown type: ${value.getType()}")
}
}
private fun resolveClass(classId: ClassId): ClassDescriptor {
return module.findClassAcrossModuleDependencies(classId)
?: ErrorUtils.createErrorClass(classId.asSingleFqName().asString())
}
}
@@ -0,0 +1,27 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.name.ClassId;
import org.jetbrains.kotlin.serialization.ClassData;
public interface ClassDataFinder {
@Nullable
ClassData findClassData(@NotNull ClassId classId);
}
@@ -0,0 +1,50 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedClassDescriptor
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.serialization.ClassData
public class ClassDeserializer(private val components: DeserializationComponents) {
private val classes: (ClassKey) -> DeserializedClassDescriptor? =
components.storageManager.createMemoizedFunctionWithNullableValues { key -> createClass(key) }
// Additional ClassData parameter is needed to avoid calling ClassDataFinder#findClassData() if it is already computed at call site
public fun deserializeClass(classId: ClassId, classData: ClassData? = null): DeserializedClassDescriptor? =
classes(ClassKey(classId, classData))
private fun createClass(key: ClassKey): DeserializedClassDescriptor? {
val classId = key.classId
val classData = key.classData ?: components.classDataFinder.findClassData(classId) ?: return null
val outerContext = if (classId.isNestedClass()) {
deserializeClass(classId.getOuterClassId())?.c ?: return null
}
else {
val fragments = components.packageFragmentProvider.getPackageFragments(classId.getPackageFqName())
assert(fragments.size() == 1) { "There should be exactly one package: $fragments, class id is $classId" }
components.createContext(fragments.single(), classData.getNameResolver())
}
return DeserializedClassDescriptor(outerContext, classData.getClassProto(), classData.getNameResolver())
}
private data class ClassKey(val classId: ClassId, classData: ClassData?) {
// This property is not declared in the constructor because it shouldn't participate in equals/hashCode
val classData: ClassData? = classData
}
}
@@ -0,0 +1,83 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.resolve.scopes.JetScope
import org.jetbrains.kotlin.types.*
import org.jetbrains.kotlin.utils.toReadOnlyList
class DeserializedType(
c: DeserializationContext,
private val typeProto: ProtoBuf.Type
) : AbstractJetType(), LazyType {
private val typeDeserializer = c.typeDeserializer
private val constructor = c.storageManager.createLazyValue {
typeDeserializer.typeConstructor(typeProto)
}
private val arguments = c.storageManager.createLazyValue {
typeProto.getArgumentList().mapIndexed {
index, proto ->
typeDeserializer.typeArgument(getConstructor().getParameters().getOrNull(index), proto)
}.toReadOnlyList()
}
private val memberScope = c.storageManager.createLazyValue {
computeMemberScope()
}
override fun getConstructor(): TypeConstructor = constructor()
override fun getArguments(): List<TypeProjection> = arguments()
override fun isMarkedNullable(): Boolean = typeProto.getNullable()
private fun computeMemberScope(): JetScope =
if (isError()) {
ErrorUtils.createErrorScope(getConstructor().toString())
}
else {
getTypeMemberScope(getConstructor(), getArguments())
}
private fun getTypeMemberScope(constructor: TypeConstructor, typeArguments: List<TypeProjection>): JetScope {
val descriptor = constructor.getDeclarationDescriptor()
return when (descriptor) {
is TypeParameterDescriptor -> descriptor.getDefaultType().getMemberScope()
is ClassDescriptor -> descriptor.getMemberScope(typeArguments)
else -> throw IllegalStateException("Unsupported classifier: $descriptor")
}
}
override fun getMemberScope(): JetScope = memberScope()
override fun isError(): Boolean {
val descriptor = getConstructor().getDeclarationDescriptor()
return descriptor != null && ErrorUtils.isError(descriptor)
}
override fun getAnnotations(): Annotations = Annotations.EMPTY
private fun <E: Any> List<E>.getOrNull(index: Int): E? {
return if (index in indices) this[index] else null
}
}
@@ -0,0 +1,35 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor;
import org.jetbrains.kotlin.descriptors.ClassDescriptor;
import org.jetbrains.kotlin.name.ClassId;
import java.util.List;
public interface ErrorReporter {
void reportIncompatibleAbiVersion(@NotNull ClassId classId, @NotNull String filePath, int actualVersion);
void reportIncompleteHierarchy(@NotNull ClassDescriptor descriptor, @NotNull List<String> unresolvedSuperClasses);
void reportCannotInferVisibility(@NotNull CallableMemberDescriptor descriptor);
void reportLoadingError(@NotNull String message, @Nullable Exception exception);
}
@@ -0,0 +1,37 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.types.DynamicTypeCapabilities
import org.jetbrains.kotlin.types.FlexibleTypeCapabilities
trait FlexibleTypeCapabilitiesDeserializer {
object ThrowException : FlexibleTypeCapabilitiesDeserializer {
override fun capabilitiesById(id: String): FlexibleTypeCapabilities? {
throw IllegalArgumentException("Capabilities not found by ThrowException manager: $id")
}
}
object Dynamic : FlexibleTypeCapabilitiesDeserializer {
override fun capabilitiesById(id: String): FlexibleTypeCapabilities? {
return if (id == DynamicTypeCapabilities.id) DynamicTypeCapabilities else null
}
}
fun capabilitiesById(id: String): FlexibleTypeCapabilities?
}
@@ -0,0 +1,24 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.name.ClassId
public trait LocalClassResolver {
public fun resolveLocalClass(classId: ClassId): ClassDescriptor?
}
@@ -0,0 +1,35 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.name.ClassId
import javax.inject.Inject
import kotlin.properties.Delegates
public class LocalClassResolverImpl : LocalClassResolver {
public var components: DeserializationComponents by Delegates.notNull()
Inject
public fun setDeserializationComponents(components: DeserializationComponents) {
this.components = components
}
override fun resolveLocalClass(classId: ClassId): ClassDescriptor? {
return components.deserializeClass(classId)
}
}
@@ -0,0 +1,207 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.serialization.*
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.*
import org.jetbrains.kotlin.resolve.DescriptorFactory
import org.jetbrains.kotlin.serialization.ProtoBuf.Callable
import org.jetbrains.kotlin.serialization.ProtoBuf.Callable.CallableKind.*
public class MemberDeserializer(private val c: DeserializationContext) {
public fun loadCallable(proto: Callable): CallableMemberDescriptor {
val callableKind = Flags.CALLABLE_KIND.get(proto.getFlags())
return when (callableKind) {
FUN -> loadFunction(proto)
VAL, VAR -> loadProperty(proto)
else -> throw IllegalArgumentException("Unsupported callable kind: $callableKind")
}
}
private fun loadProperty(proto: Callable): PropertyDescriptor {
val flags = proto.getFlags()
val property = DeserializedPropertyDescriptor(
c.containingDeclaration, null,
getAnnotations(proto, flags, AnnotatedCallableKind.PROPERTY),
modality(Flags.MODALITY.get(flags)),
visibility(Flags.VISIBILITY.get(flags)),
Flags.CALLABLE_KIND.get(flags) == Callable.CallableKind.VAR,
c.nameResolver.getName(proto.getName()),
memberKind(Flags.MEMBER_KIND.get(flags)),
proto,
c.nameResolver
)
val local = c.childContext(property, proto.getTypeParameterList())
property.setType(
local.typeDeserializer.type(proto.getReturnType()),
local.typeDeserializer.ownTypeParameters,
getDispatchReceiverParameter(),
if (proto.hasReceiverType()) local.typeDeserializer.type(proto.getReceiverType()) else null
)
val getter = if (Flags.HAS_GETTER.get(flags)) {
val getterFlags = proto.getGetterFlags()
val isNotDefault = proto.hasGetterFlags() && Flags.IS_NOT_DEFAULT.get(getterFlags)
val getter = if (isNotDefault) {
PropertyGetterDescriptorImpl(
property,
getAnnotations(proto, getterFlags, AnnotatedCallableKind.PROPERTY_GETTER),
modality(Flags.MODALITY.get(getterFlags)),
visibility(Flags.VISIBILITY.get(getterFlags)),
/* hasBody = */ isNotDefault,
/* isDefault = */ !isNotDefault,
property.getKind(), null, SourceElement.NO_SOURCE
)
}
else {
DescriptorFactory.createDefaultGetter(property)
}
getter.initialize(property.getReturnType())
getter
}
else {
null
}
val setter = if (Flags.HAS_SETTER.get(flags)) {
val setterFlags = proto.getSetterFlags()
val isNotDefault = proto.hasSetterFlags() && Flags.IS_NOT_DEFAULT.get(setterFlags)
if (isNotDefault) {
val setter = PropertySetterDescriptorImpl(
property,
getAnnotations(proto, setterFlags, AnnotatedCallableKind.PROPERTY_SETTER),
modality(Flags.MODALITY.get(setterFlags)),
visibility(Flags.VISIBILITY.get(setterFlags)),
/* hasBody = */ isNotDefault,
/* isDefault = */ !isNotDefault,
property.getKind(), null, SourceElement.NO_SOURCE
)
val setterLocal = local.childContext(setter, listOf())
val valueParameters = setterLocal.memberDeserializer.valueParameters(proto, AnnotatedCallableKind.PROPERTY_SETTER)
setter.initialize(valueParameters.single())
setter
}
else {
DescriptorFactory.createDefaultSetter(property)
}
}
else {
null
}
if (Flags.HAS_CONSTANT.get(flags)) {
property.setCompileTimeInitializer(
c.storageManager.createNullableLazyValue {
val container = c.containingDeclaration.asProtoContainer()
c.components.annotationAndConstantLoader.loadPropertyConstant(container, proto, c.nameResolver, property.getReturnType())
}
)
}
property.initialize(getter, setter)
return property
}
private fun loadFunction(proto: Callable): CallableMemberDescriptor {
val annotations = getAnnotations(proto, proto.getFlags(), AnnotatedCallableKind.FUNCTION)
val function = DeserializedSimpleFunctionDescriptor.create(c.containingDeclaration, proto, c.nameResolver, annotations)
val local = c.childContext(function, proto.getTypeParameterList())
function.initialize(
if (proto.hasReceiverType()) local.typeDeserializer.type(proto.getReceiverType()) else null,
getDispatchReceiverParameter(),
local.typeDeserializer.ownTypeParameters,
local.memberDeserializer.valueParameters(proto, AnnotatedCallableKind.FUNCTION),
local.typeDeserializer.type(proto.getReturnType()),
modality(Flags.MODALITY.get(proto.getFlags())),
visibility(Flags.VISIBILITY.get(proto.getFlags()))
)
return function
}
private fun getDispatchReceiverParameter(): ReceiverParameterDescriptor? {
return (c.containingDeclaration as? ClassDescriptor)?.getThisAsReceiverParameter()
}
public fun loadConstructor(proto: Callable, isPrimary: Boolean): ConstructorDescriptor {
val classDescriptor = c.containingDeclaration as ClassDescriptor
val descriptor = ConstructorDescriptorImpl.create(
classDescriptor, getAnnotations(proto, proto.getFlags(), AnnotatedCallableKind.FUNCTION),
isPrimary, SourceElement.NO_SOURCE
)
val local = c.childContext(descriptor, listOf())
descriptor.initialize(
classDescriptor.getTypeConstructor().getParameters(),
local.memberDeserializer.valueParameters(proto, AnnotatedCallableKind.FUNCTION),
visibility(Flags.VISIBILITY.get(proto.getFlags()))
)
descriptor.setReturnType(local.typeDeserializer.type(proto.getReturnType()))
return descriptor
}
private fun getAnnotations(proto: Callable, flags: Int, kind: AnnotatedCallableKind): Annotations {
if (!Flags.HAS_ANNOTATIONS.get(flags)) {
return Annotations.EMPTY
}
return DeserializedAnnotations(c.storageManager) {
c.components.annotationAndConstantLoader.loadCallableAnnotations(
c.containingDeclaration.asProtoContainer(), proto, c.nameResolver, kind
)
}
}
private fun valueParameters(callable: Callable, kind: AnnotatedCallableKind): List<ValueParameterDescriptor> {
val containerOfCallable = c.containingDeclaration.getContainingDeclaration().asProtoContainer()
return callable.getValueParameterList().withIndices().map { val (i, proto) = it
ValueParameterDescriptorImpl(
c.containingDeclaration, null, i,
getParameterAnnotations(containerOfCallable, callable, kind, proto),
c.nameResolver.getName(proto.getName()),
c.typeDeserializer.type(proto.getType()),
Flags.DECLARES_DEFAULT_VALUE.get(proto.getFlags()),
if (proto.hasVarargElementType()) c.typeDeserializer.type(proto.getVarargElementType()) else null,
SourceElement.NO_SOURCE
)
}
}
private fun getParameterAnnotations(
container: ProtoContainer,
callable: Callable,
kind: AnnotatedCallableKind,
valueParameter: Callable.ValueParameter
): Annotations {
if (!Flags.HAS_ANNOTATIONS.get(valueParameter.getFlags())) {
return Annotations.EMPTY
}
return DeserializedAnnotations(c.storageManager) {
c.components.annotationAndConstantLoader.loadValueParameterAnnotations(container, callable, c.nameResolver, kind, valueParameter)
}
}
private fun DeclarationDescriptor.asProtoContainer(): ProtoContainer = when(this) {
is PackageFragmentDescriptor -> ProtoContainer(null, fqName)
is DeserializedClassDescriptor -> ProtoContainer(classProto, null)
else -> error("Only members in classes or package fragments should be serialized: $this")
}
}
@@ -0,0 +1,114 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.name.ClassId;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.serialization.ProtoBuf;
import org.jetbrains.kotlin.utils.UtilsPackage;
import java.io.IOException;
import java.io.InputStream;
import java.util.LinkedList;
import static org.jetbrains.kotlin.serialization.ProtoBuf.QualifiedNameTable.QualifiedName;
public class NameResolver {
@NotNull
public static NameResolver read(@NotNull InputStream in) {
try {
ProtoBuf.StringTable simpleNames = ProtoBuf.StringTable.parseDelimitedFrom(in);
ProtoBuf.QualifiedNameTable qualifiedNames = ProtoBuf.QualifiedNameTable.parseDelimitedFrom(in);
return new NameResolver(simpleNames, qualifiedNames);
}
catch (IOException e) {
throw UtilsPackage.rethrow(e);
}
}
private final ProtoBuf.StringTable strings;
private final ProtoBuf.QualifiedNameTable qualifiedNames;
public NameResolver(
@NotNull ProtoBuf.StringTable strings,
@NotNull ProtoBuf.QualifiedNameTable qualifiedNames
) {
this.strings = strings;
this.qualifiedNames = qualifiedNames;
}
@NotNull
public ProtoBuf.StringTable getStringTable() {
return strings;
}
@NotNull
public ProtoBuf.QualifiedNameTable getQualifiedNameTable() {
return qualifiedNames;
}
@NotNull
public String getString(int index) {
return strings.getString(index);
}
@NotNull
public Name getName(int index) {
String name = strings.getString(index);
return Name.guess(name);
}
@NotNull
public ClassId getClassId(int index) {
LinkedList<String> packageFqName = new LinkedList<String>();
LinkedList<String> relativeClassName = new LinkedList<String>();
boolean local = false;
while (index != -1) {
QualifiedName proto = qualifiedNames.getQualifiedName(index);
String shortName = strings.getString(proto.getShortName());
switch (proto.getKind()) {
case CLASS:
relativeClassName.addFirst(shortName);
break;
case PACKAGE:
packageFqName.addFirst(shortName);
break;
case LOCAL:
relativeClassName.addFirst(shortName);
local = true;
break;
}
index = proto.getParentQualifiedName();
}
return new ClassId(FqName.fromSegments(packageFqName), FqName.fromSegments(relativeClassName), local);
}
@NotNull
public FqName getFqName(int index) {
QualifiedName qualifiedName = qualifiedNames.getQualifiedName(index);
Name shortName = getName(qualifiedName.getShortName());
if (!qualifiedName.hasParentQualifiedName()) {
return FqName.topLevel(shortName);
}
return getFqName(qualifiedName.getParentQualifiedName()).child(shortName);
}
}
@@ -0,0 +1,32 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.serialization.ProtoBuf
public data class ProtoContainer(val classProto: ProtoBuf.Class?, val packageFqName: FqName?) {
init {
assert((classProto != null) xor (packageFqName != null))
}
fun getFqName(nameResolver: NameResolver): FqName {
if (packageFqName != null) return packageFqName
return nameResolver.getClassId(classProto!!.getFqName()).asSingleFqName()
}
}
@@ -0,0 +1,113 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedTypeParameterDescriptor
import org.jetbrains.kotlin.types.*
import org.jetbrains.kotlin.utils.toReadOnlyList
import java.util.LinkedHashMap
public class TypeDeserializer(
private val c: DeserializationContext,
private val parent: TypeDeserializer?,
private val typeParameterProtos: List<ProtoBuf.TypeParameter>,
private val debugName: String
) {
private val classDescriptors: (Int) -> ClassDescriptor? = c.storageManager.createMemoizedFunctionWithNullableValues {
fqNameIndex -> computeClassDescriptor(fqNameIndex)
}
private val typeParameterDescriptors = c.storageManager.createLazyValue {
if (typeParameterProtos.isEmpty()) {
mapOf<Int, TypeParameterDescriptor>()
}
else {
val result = LinkedHashMap<Int, TypeParameterDescriptor>()
for ((index, proto) in typeParameterProtos.withIndices()) {
result[proto.getId()] = DeserializedTypeParameterDescriptor(c, proto, index)
}
result
}
}
val ownTypeParameters: List<TypeParameterDescriptor>
get() = typeParameterDescriptors().values().toReadOnlyList()
fun type(proto: ProtoBuf.Type): JetType {
if (proto.hasFlexibleTypeCapabilitiesId()) {
val id = c.nameResolver.getString(proto.getFlexibleTypeCapabilitiesId())
val capabilities = c.components.flexibleTypeCapabilitiesDeserializer.capabilitiesById(id)
if (capabilities == null) {
return ErrorUtils.createErrorType("${DeserializedType(c, proto)}: Capabilities not found for id $id")
}
return DelegatingFlexibleType.create(
DeserializedType(c, proto),
DeserializedType(c, proto.getFlexibleUpperBound()),
capabilities
)
}
return DeserializedType(c, proto)
}
fun typeConstructor(proto: ProtoBuf.Type): TypeConstructor {
val constructorProto = proto.getConstructor()
val id = constructorProto.getId()
return typeConstructor(constructorProto) ?: ErrorUtils.createErrorType(
if (constructorProto.getKind() == ProtoBuf.Type.Constructor.Kind.CLASS)
c.nameResolver.getClassId(id).asSingleFqName().asString()
else
"Unknown type parameter $id"
).getConstructor()
}
private fun typeConstructor(proto: ProtoBuf.Type.Constructor): TypeConstructor? = when (proto.getKind()) {
ProtoBuf.Type.Constructor.Kind.CLASS -> classDescriptors(proto.getId())?.getTypeConstructor()
ProtoBuf.Type.Constructor.Kind.TYPE_PARAMETER -> typeParameterTypeConstructor(proto)
else -> throw IllegalStateException("Unknown kind ${proto.getKind()}")
}
private fun typeParameterTypeConstructor(proto: ProtoBuf.Type.Constructor): TypeConstructor? =
typeParameterDescriptors().get(proto.getId())?.getTypeConstructor() ?:
parent?.typeParameterTypeConstructor(proto)
private fun computeClassDescriptor(fqNameIndex: Int): ClassDescriptor? {
val id = c.nameResolver.getClassId(fqNameIndex)
if (id.isLocal()) {
// Local classes can't be found in scopes
return c.components.localClassResolver.resolveLocalClass(id)
}
return c.components.moduleDescriptor.findClassAcrossModuleDependencies(id)
}
fun typeArgument(parameter: TypeParameterDescriptor?, typeArgumentProto: ProtoBuf.Type.Argument): TypeProjection {
return if (typeArgumentProto.getProjection() == ProtoBuf.Type.Argument.Projection.STAR)
if (parameter == null)
TypeBasedStarProjectionImpl(KotlinBuiltIns.getInstance().getNullableAnyType())
else
StarProjectionImpl(parameter)
else TypeProjectionImpl(variance(typeArgumentProto.getProjection()), type(typeArgumentProto.getType()))
}
override fun toString() = debugName + (if (parent == null) "" else ". Child of ${parent.debugName}")
}
@@ -0,0 +1,65 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.storage.StorageManager
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.resolve.constants.CompileTimeConstant
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
public class DeserializationComponents(
public val storageManager: StorageManager,
public val moduleDescriptor: ModuleDescriptor,
public val classDataFinder: ClassDataFinder,
public val annotationAndConstantLoader: AnnotationAndConstantLoader<AnnotationDescriptor, CompileTimeConstant<*>>,
public val packageFragmentProvider: PackageFragmentProvider,
public val localClassResolver: LocalClassResolver,
public val flexibleTypeCapabilitiesDeserializer: FlexibleTypeCapabilitiesDeserializer
) {
public val classDeserializer: ClassDeserializer = ClassDeserializer(this)
public fun deserializeClass(classId: ClassId): ClassDescriptor? = classDeserializer.deserializeClass(classId)
public fun createContext(descriptor: PackageFragmentDescriptor, nameResolver: NameResolver): DeserializationContext =
DeserializationContext(this, nameResolver, descriptor, parentTypeDeserializer = null, typeParameters = listOf())
}
public class DeserializationContext(
public val components: DeserializationComponents,
public val nameResolver: NameResolver,
public val containingDeclaration: DeclarationDescriptor,
parentTypeDeserializer: TypeDeserializer?,
typeParameters: List<ProtoBuf.TypeParameter>
) {
val typeDeserializer = TypeDeserializer(this, parentTypeDeserializer, typeParameters,
"Deserializer for ${containingDeclaration.getName()}")
val memberDeserializer = MemberDeserializer(this)
val storageManager: StorageManager get() = components.storageManager
fun childContext(
descriptor: DeclarationDescriptor,
typeParameterProtos: List<ProtoBuf.TypeParameter>,
nameResolver: NameResolver = this.nameResolver
) = DeserializationContext(
components, nameResolver, descriptor, parentTypeDeserializer = this.typeDeserializer, typeParameters = typeParameterProtos
)
}
@@ -0,0 +1,42 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.utils.toReadOnlyList
import org.jetbrains.kotlin.storage.StorageManager
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.resolve.DescriptorUtils
class DeserializedAnnotations(
storageManager: StorageManager,
compute: () -> List<AnnotationDescriptor>
) : Annotations {
private val annotations = storageManager.createLazyValue { compute().toReadOnlyList() }
override fun isEmpty(): Boolean = annotations().isEmpty()
override fun findAnnotation(fqName: FqName): AnnotationDescriptor? = annotations().firstOrNull {
annotation ->
val descriptor = annotation.getType().getConstructor().getDeclarationDescriptor()
descriptor is ClassDescriptor && fqName.equalsTo(DescriptorUtils.getFqName(descriptor))
}
override fun iterator(): Iterator<AnnotationDescriptor> = annotations().iterator()
}
@@ -0,0 +1,26 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor
public trait DeserializedCallableMemberDescriptor: CallableMemberDescriptor {
public val proto: ProtoBuf.Callable
public val nameResolver: NameResolver
}
@@ -0,0 +1,319 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.AbstractClassDescriptor
import org.jetbrains.kotlin.descriptors.impl.EnumEntrySyntheticClassDescriptor
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.DescriptorFactory
import org.jetbrains.kotlin.resolve.OverridingUtil
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
import org.jetbrains.kotlin.resolve.scopes.JetScope
import org.jetbrains.kotlin.resolve.scopes.StaticScopeForKotlinClass
import org.jetbrains.kotlin.serialization.Flags
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.serialization.deserialization.DeserializationContext
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.types.AbstractClassTypeConstructor
import org.jetbrains.kotlin.types.JetType
import org.jetbrains.kotlin.utils.addIfNotNull
import org.jetbrains.kotlin.utils.singletonOrEmptyList
import java.util.ArrayList
import java.util.HashSet
import java.util.LinkedHashSet
public class DeserializedClassDescriptor(
outerContext: DeserializationContext,
val classProto: ProtoBuf.Class,
nameResolver: NameResolver
) : ClassDescriptor, AbstractClassDescriptor(
outerContext.storageManager,
nameResolver.getClassId(classProto.getFqName()).getShortClassName()
) {
private val modality = deserialization.modality(Flags.MODALITY.get(classProto.getFlags()))
private val visibility = deserialization.visibility(Flags.VISIBILITY.get(classProto.getFlags()))
private val kindFromProto = Flags.CLASS_KIND.get(classProto.getFlags())
private val kind = deserialization.classKind(kindFromProto)
private val isCompanion = kindFromProto == ProtoBuf.Class.Kind.CLASS_OBJECT
private val isInner = Flags.INNER.get(classProto.getFlags())
val c = outerContext.childContext(this, classProto.getTypeParameterList(), nameResolver)
private val classId = nameResolver.getClassId(classProto.getFqName())
private val staticScope = StaticScopeForKotlinClass(this)
private val typeConstructor = DeserializedClassTypeConstructor()
private val memberScope = DeserializedClassMemberScope()
private val nestedClasses = NestedClassDescriptors()
private val enumEntries = EnumEntryClassDescriptors()
private val containingDeclaration = outerContext.containingDeclaration
private val primaryConstructor = c.storageManager.createNullableLazyValue { computePrimaryConstructor() }
private val constructors = c.storageManager.createLazyValue { computeConstructors() }
private val companionObjectDescriptor = c.storageManager.createNullableLazyValue { computeCompanionObjectDescriptor() }
private val annotations =
if (!Flags.HAS_ANNOTATIONS.get(classProto.getFlags())) {
Annotations.EMPTY
}
else DeserializedAnnotations(c.storageManager) {
c.components.annotationAndConstantLoader.loadClassAnnotations(classProto, c.nameResolver)
}
override fun getContainingDeclaration(): DeclarationDescriptor = containingDeclaration
override fun getTypeConstructor() = typeConstructor
override fun getKind() = kind
override fun getModality() = modality
override fun getVisibility() = visibility
override fun isInner() = isInner
override fun getAnnotations() = annotations
override fun getScopeForMemberLookup() = memberScope
override fun getStaticScope() = staticScope
override fun isCompanionObject(): Boolean = isCompanion
private fun computePrimaryConstructor(): ConstructorDescriptor? {
if (!classProto.hasPrimaryConstructor()) return null
val constructorProto = classProto.getPrimaryConstructor()
if (!constructorProto.hasData()) {
val descriptor = DescriptorFactory.createPrimaryConstructorForObject(this, SourceElement.NO_SOURCE)
descriptor.setReturnType(getDefaultType())
return descriptor
}
return c.memberDeserializer.loadConstructor(constructorProto.getData(), true)
}
override fun getUnsubstitutedPrimaryConstructor(): ConstructorDescriptor? = primaryConstructor()
private fun computeConstructors(): Collection<ConstructorDescriptor> =
computeSecondaryConstructors() + getUnsubstitutedPrimaryConstructor().singletonOrEmptyList()
private fun computeSecondaryConstructors(): List<ConstructorDescriptor> =
classProto.getSecondaryConstructorList().map {
c.memberDeserializer.loadConstructor(it, false)
}
override fun getConstructors() = constructors()
private fun computeCompanionObjectDescriptor(): ClassDescriptor? {
if (!classProto.hasCompanionObjectName()) return null
val companionObjectName = c.nameResolver.getName(classProto.getCompanionObjectName())
return memberScope.getClassifier(companionObjectName) as? ClassDescriptor
}
override fun getCompanionObjectDescriptor(): ClassDescriptor? = companionObjectDescriptor()
private fun computeSuperTypes(): Collection<JetType> {
val supertypes = ArrayList<JetType>(classProto.getSupertypeCount())
for (supertype in classProto.getSupertypeList()) {
supertypes.add(c.typeDeserializer.type(supertype))
}
return supertypes
}
override fun toString() = "deserialized class ${getName().toString()}" // not using descriptor render to preserve laziness
override fun getSource() = SourceElement.NO_SOURCE
private inner class DeserializedClassTypeConstructor : AbstractClassTypeConstructor() {
private val supertypes = computeSuperTypes()
override fun getParameters() = c.typeDeserializer.ownTypeParameters
override fun getSupertypes(): Collection<JetType> {
// We cannot have error supertypes because subclasses inherit error functions from them
// Filtering right away means copying the list every time, so we check for the rare condition first, and only then filter
for (supertype in supertypes) {
if (supertype.isError()) {
return supertypes.filter { !it.isError() }
}
}
return supertypes
}
override fun isFinal() = !getModality().isOverridable()
override fun isDenotable() = true
override fun getDeclarationDescriptor() = this@DeserializedClassDescriptor
override fun getAnnotations(): Annotations = Annotations.EMPTY // TODO
override fun toString() = getName().toString()
}
private inner class DeserializedClassMemberScope : DeserializedMemberScope(c, classProto.getMemberList()) {
private val classDescriptor: DeserializedClassDescriptor get() = this@DeserializedClassDescriptor
private val allDescriptors = c.storageManager.createLazyValue {
computeDescriptors(DescriptorKindFilter.ALL, JetScope.ALL_NAME_FILTER)
}
override fun getDescriptors(kindFilter: DescriptorKindFilter,
nameFilter: (Name) -> Boolean): Collection<DeclarationDescriptor> = allDescriptors()
override fun computeNonDeclaredFunctions(name: Name, functions: MutableCollection<FunctionDescriptor>) {
val fromSupertypes = ArrayList<FunctionDescriptor>()
for (supertype in classDescriptor.getTypeConstructor().getSupertypes()) {
fromSupertypes.addAll(supertype.getMemberScope().getFunctions(name))
}
generateFakeOverrides(name, fromSupertypes, functions)
}
override fun computeNonDeclaredProperties(name: Name, descriptors: MutableCollection<PropertyDescriptor>) {
val fromSupertypes = ArrayList<PropertyDescriptor>()
for (supertype in classDescriptor.getTypeConstructor().getSupertypes()) {
[suppress("UNCHECKED_CAST")]
fromSupertypes.addAll(supertype.getMemberScope().getProperties(name) as Collection<PropertyDescriptor>)
}
generateFakeOverrides(name, fromSupertypes, descriptors)
}
private fun <D : CallableMemberDescriptor> generateFakeOverrides(name: Name, fromSupertypes: Collection<D>, result: MutableCollection<D>) {
val fromCurrent = ArrayList<CallableMemberDescriptor>(result)
OverridingUtil.generateOverridesInFunctionGroup(name, fromSupertypes, fromCurrent, classDescriptor, object : OverridingUtil.DescriptorSink {
override fun addToScope(fakeOverride: CallableMemberDescriptor) {
// TODO: report "cannot infer visibility"
OverridingUtil.resolveUnknownVisibilityForMember(fakeOverride, null)
[suppress("UNCHECKED_CAST")]
result.add(fakeOverride as D)
}
override fun conflict(fromSuper: CallableMemberDescriptor, fromCurrent: CallableMemberDescriptor) {
// TODO report conflicts
}
})
}
override fun addNonDeclaredDescriptors(result: MutableCollection<DeclarationDescriptor>) {
for (supertype in classDescriptor.getTypeConstructor().getSupertypes()) {
for (descriptor in supertype.getMemberScope().getAllDescriptors()) {
if (descriptor is FunctionDescriptor) {
result.addAll(getFunctions(descriptor.getName()))
}
else if (descriptor is PropertyDescriptor) {
result.addAll(getProperties(descriptor.getName()))
}
// Nothing else is inherited
}
}
}
override fun getImplicitReceiver() = classDescriptor.getThisAsReceiverParameter()
override fun getClassDescriptor(name: Name): ClassifierDescriptor? =
classDescriptor.enumEntries.findEnumEntry(name) ?: classDescriptor.nestedClasses.findNestedClass(name)
override fun addClassDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean) {
result.addAll(classDescriptor.nestedClasses.all())
}
override fun addEnumEntryDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean) {
result.addAll(classDescriptor.enumEntries.all())
}
}
private inner class NestedClassDescriptors {
private val nestedClassNames = nestedClassNames()
val findNestedClass = c.storageManager.createMemoizedFunctionWithNullableValues<Name, ClassDescriptor> {
name ->
if (name in nestedClassNames) {
c.components.deserializeClass(classId.createNestedClassId(name))
}
else null
}
private fun nestedClassNames(): Set<Name> {
val result = LinkedHashSet<Name>()
val nameResolver = c.nameResolver
for (index in classProto.getNestedClassNameList()) {
result.add(nameResolver.getName(index!!))
}
return result
}
fun all(): Collection<ClassDescriptor> {
val result = ArrayList<ClassDescriptor>(nestedClassNames.size())
nestedClassNames.forEach { name -> result.addIfNotNull(findNestedClass(name)) }
return result
}
}
private inner class EnumEntryClassDescriptors {
private val enumEntryNames = enumEntryNames()
private fun enumEntryNames(): Set<Name> {
if (getKind() != ClassKind.ENUM_CLASS) return setOf()
val result = LinkedHashSet<Name>()
val nameResolver = c.nameResolver
for (index in classProto.getEnumEntryList()) {
result.add(nameResolver.getName(index!!))
}
return result
}
val findEnumEntry = c.storageManager.createMemoizedFunctionWithNullableValues<Name, ClassDescriptor> {
name ->
if (name in enumEntryNames) {
EnumEntrySyntheticClassDescriptor.create(
c.storageManager, this@DeserializedClassDescriptor, name, enumMemberNames, SourceElement.NO_SOURCE
)
}
else null
}
private val enumMemberNames = c.storageManager.createLazyValue { computeEnumMemberNames() }
private fun computeEnumMemberNames(): Collection<Name> {
// NOTE: order of enum entry members should be irrelevant
// because enum entries are effectively invisible to user (as classes)
val result = HashSet<Name>()
for (supertype in getTypeConstructor().getSupertypes()) {
for (descriptor in supertype.getMemberScope().getAllDescriptors()) {
if (descriptor is SimpleFunctionDescriptor || descriptor is PropertyDescriptor) {
result.add(descriptor.getName())
}
}
}
val nameResolver = c.nameResolver
return classProto.getMemberList().mapTo(result) { nameResolver.getName(it.getName()) }
}
fun all(): Collection<ClassDescriptor> {
val result = ArrayList<ClassDescriptor>(enumEntryNames.size())
enumEntryNames.forEach { name -> result.addIfNotNull(findEnumEntry(name)) }
return result
}
}
}
@@ -0,0 +1,197 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.serialization.Flags
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.scopes.JetScope
import org.jetbrains.kotlin.utils.Printer
import org.jetbrains.kotlin.utils.toReadOnlyList
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
import org.jetbrains.kotlin.serialization.ProtoBuf.Callable.CallableKind
import org.jetbrains.kotlin.serialization.deserialization.DeserializationContext
import java.util.*
public abstract class DeserializedMemberScope protected(
protected val c: DeserializationContext,
membersList: Collection<ProtoBuf.Callable>
) : JetScope {
private data class ProtoKey(val name: Name, val kind: Kind, val isExtension: Boolean)
private enum class Kind { FUNCTION PROPERTY }
private fun CallableKind.toKind(): Kind {
return when (this) {
CallableKind.FUN -> Kind.FUNCTION
CallableKind.VAL, CallableKind.VAR -> Kind.PROPERTY
else -> throw IllegalStateException("Unexpected CallableKind $this")
}
}
private val membersProtos =
c.storageManager.createLazyValue { groupByKey(filteredMemberProtos(membersList)) }
private val functions =
c.storageManager.createMemoizedFunction<Name, Collection<FunctionDescriptor>> { computeFunctions(it) }
private val properties =
c.storageManager.createMemoizedFunction<Name, Collection<VariableDescriptor>> { computeProperties(it) }
protected open fun filteredMemberProtos(allMemberProtos: Collection<ProtoBuf.Callable>): Collection<ProtoBuf.Callable> = allMemberProtos
private fun groupByKey(membersList: Collection<ProtoBuf.Callable>): Map<ProtoKey, List<ProtoBuf.Callable>> {
val map = LinkedHashMap<ProtoKey, MutableList<ProtoBuf.Callable>>()
for (memberProto in membersList) {
val key = ProtoKey(
c.nameResolver.getName(memberProto.getName()),
Flags.CALLABLE_KIND[memberProto.getFlags()].toKind(),
memberProto.hasReceiverType()
)
var protos = map[key]
if (protos == null) {
protos = ArrayList(1)
map.put(key, protos)
}
protos!!.add(memberProto)
}
return map
}
private fun <D : CallableMemberDescriptor> computeMembers(name: Name, kind: Kind): LinkedHashSet<D> {
val memberProtos = membersProtos()[ProtoKey(name, kind, isExtension = false)].orEmpty() +
membersProtos()[ProtoKey(name, kind, isExtension = true)].orEmpty()
[suppress("UNCHECKED_CAST")]
return memberProtos.mapTo(LinkedHashSet<D>()) { memberProto ->
c.memberDeserializer.loadCallable(memberProto) as D
}
}
private fun computeFunctions(name: Name): Collection<FunctionDescriptor> {
val descriptors = computeMembers<FunctionDescriptor>(name, Kind.FUNCTION)
computeNonDeclaredFunctions(name, descriptors)
return descriptors.toReadOnlyList()
}
protected open fun computeNonDeclaredFunctions(name: Name, functions: MutableCollection<FunctionDescriptor>) {
}
override fun getFunctions(name: Name): Collection<FunctionDescriptor> = functions(name)
private fun computeProperties(name: Name): Collection<VariableDescriptor> {
val descriptors = computeMembers<PropertyDescriptor>(name, Kind.PROPERTY)
computeNonDeclaredProperties(name, descriptors)
return descriptors.toReadOnlyList()
}
protected open fun computeNonDeclaredProperties(name: Name, descriptors: MutableCollection<PropertyDescriptor>) {
}
override fun getProperties(name: Name): Collection<VariableDescriptor> = properties.invoke(name)
override fun getClassifier(name: Name) = getClassDescriptor(name)
protected abstract fun getClassDescriptor(name: Name): ClassifierDescriptor?
protected abstract fun addClassDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean)
override fun getPackage(name: Name): PackageViewDescriptor? = null
override fun getLocalVariable(name: Name): VariableDescriptor? = null
override fun getContainingDeclaration() = c.containingDeclaration
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = listOf()
protected fun computeDescriptors(kindFilter: DescriptorKindFilter,
nameFilter: (Name) -> Boolean): Collection<DeclarationDescriptor> {
//NOTE: descriptors should be in the same order they were serialized in
// see MemberComparator
val result = LinkedHashSet<DeclarationDescriptor>(0)
if (kindFilter.acceptsKinds(DescriptorKindFilter.SINGLETON_CLASSIFIERS_MASK)) {
addEnumEntryDescriptors(result, nameFilter)
}
addFunctionsAndProperties(result, kindFilter, nameFilter)
addNonDeclaredDescriptors(result)
if (kindFilter.acceptsKinds(DescriptorKindFilter.CLASSIFIERS_MASK)) {
addClassDescriptors(result, nameFilter)
}
return result.toReadOnlyList()
}
private fun addFunctionsAndProperties(
result: LinkedHashSet<DeclarationDescriptor>,
kindFilter: DescriptorKindFilter,
nameFilter: (Name) -> Boolean
) {
val acceptsProperties = kindFilter.acceptsKinds(DescriptorKindFilter.VARIABLES_MASK)
val acceptsFunctions = kindFilter.acceptsKinds(DescriptorKindFilter.FUNCTIONS_MASK)
if (!(acceptsFunctions || acceptsProperties)) {
return
}
val keys = membersProtos().keySet().filter { nameFilter(it.name) }
if (acceptsProperties) {
addMembers(result, keys, Kind.PROPERTY) { getProperties(it) }
}
if (acceptsFunctions) {
addMembers(result, keys, Kind.FUNCTION) { getFunctions(it) }
}
}
private fun addMembers(
result: MutableCollection<DeclarationDescriptor>,
keys: Collection<ProtoKey>,
kind: Kind,
getMembers: (Name) -> Collection<CallableDescriptor>
) {
val filteredByKind = keys.filter { it.kind == kind }
listOf(false, true).forEach { isExtension ->
filteredByKind.filter { it.isExtension == isExtension }
.flatMap { getMembers(it.name) }
.filterTo(result) { (it.getExtensionReceiverParameter() != null) == isExtension }
}
}
protected abstract fun addNonDeclaredDescriptors(result: MutableCollection<DeclarationDescriptor>)
protected abstract fun addEnumEntryDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean)
override fun getImplicitReceiversHierarchy(): List<ReceiverParameterDescriptor> {
val receiver = getImplicitReceiver()
return if (receiver != null) listOf(receiver) else listOf()
}
protected abstract fun getImplicitReceiver(): ReceiverParameterDescriptor?
override fun getOwnDeclaredDescriptors() = getAllDescriptors()
override fun printScopeStructure(p: Printer) {
p.println(javaClass.getSimpleName(), " {")
p.pushIndent()
p.println("containingDeclaration = " + getContainingDeclaration())
p.popIndent()
p.println("}")
}
}
@@ -0,0 +1,63 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.DeserializationComponents
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.PackageFragmentDescriptor
import org.jetbrains.kotlin.descriptors.ReceiverParameterDescriptor
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.utils.addIfNotNull
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
public open class DeserializedPackageMemberScope(
packageDescriptor: PackageFragmentDescriptor,
proto: ProtoBuf.Package,
nameResolver: NameResolver,
components: DeserializationComponents,
classNames: () -> Collection<Name>
) : DeserializedMemberScope(components.createContext(packageDescriptor, nameResolver), proto.getMemberList()) {
private val packageFqName = packageDescriptor.fqName
private val classNames = c.storageManager.createLazyValue(classNames)
override fun getDescriptors(kindFilter: DescriptorKindFilter, nameFilter: (Name) -> Boolean)
= computeDescriptors(kindFilter, nameFilter)
override fun getClassDescriptor(name: Name) = c.components.deserializeClass(ClassId(packageFqName, name))
override fun addClassDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean) {
for (className in classNames()) {
if (nameFilter(className)) {
result.addIfNotNull(getClassDescriptor(className))
}
}
}
override fun addNonDeclaredDescriptors(result: MutableCollection<DeclarationDescriptor>) {
// Do nothing
}
override fun addEnumEntryDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean) {
// Do nothing
}
override fun getImplicitReceiver(): ReceiverParameterDescriptor? = null
}
@@ -0,0 +1,55 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.Visibility
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor.Kind
import org.jetbrains.kotlin.descriptors.SourceElement
public class DeserializedPropertyDescriptor(
containingDeclaration: DeclarationDescriptor,
original: PropertyDescriptor?,
annotations: Annotations,
modality: Modality,
visibility: Visibility,
isVar: Boolean,
name: Name,
kind: Kind,
override public val proto: ProtoBuf.Callable,
override public val nameResolver: NameResolver
) : DeserializedCallableMemberDescriptor,
PropertyDescriptorImpl(containingDeclaration, original, annotations, modality, visibility, isVar, name, kind, SourceElement.NO_SOURCE) {
override fun createSubstitutedCopy(
newOwner: DeclarationDescriptor,
newModality: Modality,
newVisibility: Visibility,
original: PropertyDescriptor?,
kind: Kind
): PropertyDescriptorImpl {
return DeserializedPropertyDescriptor(
newOwner, original, getAnnotations(), newModality, newVisibility, isVar(), getName(), kind, proto, nameResolver)
}
}
@@ -0,0 +1,106 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor;
import org.jetbrains.kotlin.descriptors.FunctionDescriptor;
import org.jetbrains.kotlin.descriptors.SimpleFunctionDescriptor;
import org.jetbrains.kotlin.descriptors.SourceElement;
import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.descriptors.impl.FunctionDescriptorImpl;
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.serialization.Flags;
import org.jetbrains.kotlin.serialization.ProtoBuf;
import org.jetbrains.kotlin.serialization.deserialization.DeserializationPackage;
import org.jetbrains.kotlin.serialization.deserialization.NameResolver;
public class DeserializedSimpleFunctionDescriptor extends SimpleFunctionDescriptorImpl implements DeserializedCallableMemberDescriptor {
private final ProtoBuf.Callable proto;
private final NameResolver nameResolver;
private DeserializedSimpleFunctionDescriptor(
@NotNull DeclarationDescriptor containingDeclaration,
@Nullable SimpleFunctionDescriptor original,
@NotNull Annotations annotations,
@NotNull Name name,
@NotNull Kind kind,
@NotNull ProtoBuf.Callable proto,
@NotNull NameResolver nameResolver
) {
super(containingDeclaration, original, annotations, name, kind, SourceElement.NO_SOURCE);
this.proto = proto;
this.nameResolver = nameResolver;
}
@NotNull
@Override
protected FunctionDescriptorImpl createSubstitutedCopy(
@NotNull DeclarationDescriptor newOwner,
@Nullable FunctionDescriptor original,
@NotNull Kind kind
) {
return new DeserializedSimpleFunctionDescriptor(
newOwner,
(DeserializedSimpleFunctionDescriptor) original,
getAnnotations(),
getName(),
kind,
proto,
nameResolver
);
}
@NotNull
@Override
public DeserializedSimpleFunctionDescriptor getOriginal() {
return (DeserializedSimpleFunctionDescriptor) super.getOriginal();
}
@NotNull
@Override
public ProtoBuf.Callable getProto() {
return proto;
}
@NotNull
@Override
public NameResolver getNameResolver() {
return nameResolver;
}
@NotNull
public static DeserializedSimpleFunctionDescriptor create(
@NotNull DeclarationDescriptor containingDeclaration,
@NotNull ProtoBuf.Callable proto,
@NotNull NameResolver nameResolver,
@NotNull Annotations annotations
) {
return new DeserializedSimpleFunctionDescriptor(
containingDeclaration,
null,
annotations,
nameResolver.getName(proto.getName()),
DeserializationPackage.memberKind(Flags.MEMBER_KIND.get(proto.getFlags())),
proto,
nameResolver
);
}
}
@@ -0,0 +1,61 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization.descriptors;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.builtins.KotlinBuiltIns;
import org.jetbrains.kotlin.descriptors.SourceElement;
import org.jetbrains.kotlin.descriptors.impl.AbstractLazyTypeParameterDescriptor;
import org.jetbrains.kotlin.serialization.ProtoBuf;
import org.jetbrains.kotlin.serialization.deserialization.DeserializationContext;
import org.jetbrains.kotlin.serialization.deserialization.DeserializationPackage;
import org.jetbrains.kotlin.serialization.deserialization.TypeDeserializer;
import org.jetbrains.kotlin.types.JetType;
import java.util.Collections;
import java.util.LinkedHashSet;
import java.util.Set;
public class DeserializedTypeParameterDescriptor extends AbstractLazyTypeParameterDescriptor {
private final ProtoBuf.TypeParameter proto;
private final TypeDeserializer typeDeserializer;
public DeserializedTypeParameterDescriptor(@NotNull DeserializationContext c, @NotNull ProtoBuf.TypeParameter proto, int index) {
super(c.getStorageManager(),
c.getContainingDeclaration(),
c.getNameResolver().getName(proto.getName()),
DeserializationPackage.variance(proto.getVariance()),
proto.getReified(),
index,
SourceElement.NO_SOURCE);
this.proto = proto;
this.typeDeserializer = c.getTypeDeserializer();
}
@NotNull
@Override
protected Set<JetType> resolveUpperBounds() {
if (proto.getUpperBoundCount() == 0) {
return Collections.singleton(KotlinBuiltIns.getInstance().getDefaultBound());
}
Set<JetType> result = new LinkedHashSet<JetType>(proto.getUpperBoundCount());
for (ProtoBuf.Type upperBound : proto.getUpperBoundList()) {
result.add(typeDeserializer.type(upperBound));
}
return result;
}
}
@@ -0,0 +1,34 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.name.SpecialNames
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
import org.jetbrains.kotlin.name.ClassId
public fun ModuleDescriptor.findClassAcrossModuleDependencies(classId: ClassId): ClassDescriptor? {
val packageViewDescriptor = getPackage(classId.getPackageFqName()) ?: return null
val segments = classId.getRelativeClassName().pathSegments()
val topLevelClass = packageViewDescriptor.getMemberScope().getClassifier(segments.first()) as? ClassDescriptor ?: return null
var result = topLevelClass
for (name in segments.subList(1, segments.size())) {
result = result.getUnsubstitutedInnerClassesScope().getClassifier(name) as? ClassDescriptor ?: return null
}
return result
}
@@ -0,0 +1,69 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.serialization.deserialization
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.descriptors.Visibilities
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.serialization.ProtoBuf.TypeParameter
import org.jetbrains.kotlin.types.Variance
fun memberKind(memberKind: ProtoBuf.Callable.MemberKind) = when (memberKind) {
ProtoBuf.Callable.MemberKind.DECLARATION -> CallableMemberDescriptor.Kind.DECLARATION
ProtoBuf.Callable.MemberKind.FAKE_OVERRIDE -> CallableMemberDescriptor.Kind.FAKE_OVERRIDE
ProtoBuf.Callable.MemberKind.DELEGATION -> CallableMemberDescriptor.Kind.DELEGATION
ProtoBuf.Callable.MemberKind.SYNTHESIZED -> CallableMemberDescriptor.Kind.SYNTHESIZED
}
fun modality(modality: ProtoBuf.Modality) = when (modality) {
ProtoBuf.Modality.FINAL -> Modality.FINAL
ProtoBuf.Modality.OPEN -> Modality.OPEN
ProtoBuf.Modality.ABSTRACT -> Modality.ABSTRACT
}
fun visibility(visibility: ProtoBuf.Visibility) = when (visibility) {
ProtoBuf.Visibility.INTERNAL -> Visibilities.INTERNAL
ProtoBuf.Visibility.PRIVATE -> Visibilities.PRIVATE
ProtoBuf.Visibility.PRIVATE_TO_THIS -> Visibilities.PRIVATE_TO_THIS
ProtoBuf.Visibility.PROTECTED -> Visibilities.PROTECTED
ProtoBuf.Visibility.PUBLIC -> Visibilities.PUBLIC
ProtoBuf.Visibility.LOCAL -> Visibilities.LOCAL
}
public fun classKind(kind: ProtoBuf.Class.Kind): ClassKind = when (kind) {
ProtoBuf.Class.Kind.CLASS -> ClassKind.CLASS
ProtoBuf.Class.Kind.TRAIT -> ClassKind.TRAIT
ProtoBuf.Class.Kind.ENUM_CLASS -> ClassKind.ENUM_CLASS
ProtoBuf.Class.Kind.ENUM_ENTRY -> ClassKind.ENUM_ENTRY
ProtoBuf.Class.Kind.ANNOTATION_CLASS -> ClassKind.ANNOTATION_CLASS
ProtoBuf.Class.Kind.OBJECT, ProtoBuf.Class.Kind.CLASS_OBJECT -> ClassKind.OBJECT
}
fun variance(variance: TypeParameter.Variance) = when (variance) {
ProtoBuf.TypeParameter.Variance.IN -> Variance.IN_VARIANCE
ProtoBuf.TypeParameter.Variance.OUT -> Variance.OUT_VARIANCE
ProtoBuf.TypeParameter.Variance.INV -> Variance.INVARIANT
}
fun variance(variance: ProtoBuf.Type.Argument.Projection) = when (variance) {
ProtoBuf.Type.Argument.Projection.IN -> Variance.IN_VARIANCE
ProtoBuf.Type.Argument.Projection.OUT -> Variance.OUT_VARIANCE
ProtoBuf.Type.Argument.Projection.INV -> Variance.INVARIANT
else -> throw IllegalArgumentException("Only IN, OUT and INV are supported. Actual argument: $variance")
}