diff --git a/compiler/backend/src/org/jetbrains/kotlin/codegen/serialization/JvmSerializerExtension.java b/compiler/backend/src/org/jetbrains/kotlin/codegen/serialization/JvmSerializerExtension.java
index 8ceaceed003..1d1421a91b4 100644
--- a/compiler/backend/src/org/jetbrains/kotlin/codegen/serialization/JvmSerializerExtension.java
+++ b/compiler/backend/src/org/jetbrains/kotlin/codegen/serialization/JvmSerializerExtension.java
@@ -25,11 +25,13 @@ import org.jetbrains.kotlin.codegen.state.JetTypeMapper;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor;
import org.jetbrains.kotlin.load.java.lazy.types.RawTypeCapabilities;
+import org.jetbrains.kotlin.name.ClassId;
import org.jetbrains.kotlin.serialization.AnnotationSerializer;
import org.jetbrains.kotlin.serialization.ProtoBuf;
import org.jetbrains.kotlin.serialization.SerializerExtension;
import org.jetbrains.kotlin.serialization.StringTable;
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf;
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBufUtil;
import org.jetbrains.kotlin.types.JetType;
import org.jetbrains.org.objectweb.asm.Type;
import org.jetbrains.org.objectweb.asm.commons.Method;
@@ -85,7 +87,10 @@ public class JvmSerializerExtension extends SerializerExtension {
public void serializeConstructor(@NotNull ConstructorDescriptor descriptor, @NotNull ProtoBuf.Constructor.Builder proto) {
Method method = bindings.get(METHOD_FOR_FUNCTION, descriptor);
if (method != null) {
- proto.setExtension(JvmProtoBuf.constructorSignature, new SignatureSerializer().methodSignature(method));
+ JvmProtoBuf.JvmMethodSignature signature = new SignatureSerializer().methodSignature(descriptor, method);
+ if (signature != null) {
+ proto.setExtension(JvmProtoBuf.constructorSignature, signature);
+ }
}
saveImplClassName(descriptor, proto);
@@ -95,7 +100,10 @@ public class JvmSerializerExtension extends SerializerExtension {
public void serializeFunction(@NotNull FunctionDescriptor descriptor, @NotNull ProtoBuf.Function.Builder proto) {
Method method = bindings.get(METHOD_FOR_FUNCTION, descriptor);
if (method != null) {
- proto.setExtension(JvmProtoBuf.methodSignature, new SignatureSerializer().methodSignature(method));
+ JvmProtoBuf.JvmMethodSignature signature = new SignatureSerializer().methodSignature(descriptor, method);
+ if (signature != null) {
+ proto.setExtension(JvmProtoBuf.methodSignature, signature);
+ }
}
saveImplClassName(descriptor, proto);
@@ -129,9 +137,9 @@ public class JvmSerializerExtension extends SerializerExtension {
JvmProtoBuf.JvmPropertySignature signature = signatureSerializer.propertySignature(
fieldName, fieldDesc, isStaticInOuter,
- syntheticMethod != null ? signatureSerializer.methodSignature(syntheticMethod) : null,
- getterMethod != null ? signatureSerializer.methodSignature(getterMethod) : null,
- setterMethod != null ? signatureSerializer.methodSignature(setterMethod) : null
+ syntheticMethod != null ? signatureSerializer.methodSignature(null, syntheticMethod) : null,
+ getterMethod != null ? signatureSerializer.methodSignature(null, getterMethod) : null,
+ setterMethod != null ? signatureSerializer.methodSignature(null, setterMethod) : null
);
proto.setExtension(JvmProtoBuf.propertySignature, signature);
@@ -153,12 +161,67 @@ public class JvmSerializerExtension extends SerializerExtension {
}
private class SignatureSerializer {
- @NotNull
- public JvmProtoBuf.JvmMethodSignature methodSignature(@NotNull Method method) {
- return JvmProtoBuf.JvmMethodSignature.newBuilder()
- .setName(stringTable.getStringIndex(method.getName()))
- .setDesc(stringTable.getStringIndex(method.getDescriptor()))
- .build();
+ @Nullable
+ public JvmProtoBuf.JvmMethodSignature methodSignature(@Nullable FunctionDescriptor descriptor, @NotNull Method method) {
+ JvmProtoBuf.JvmMethodSignature.Builder builder = JvmProtoBuf.JvmMethodSignature.newBuilder();
+ if (descriptor == null || !descriptor.getName().asString().equals(method.getName())) {
+ builder.setName(stringTable.getStringIndex(method.getName()));
+ }
+ if (descriptor == null || requiresSignature(descriptor, method.getDescriptor())) {
+ builder.setDesc(stringTable.getStringIndex(method.getDescriptor()));
+ }
+ return builder.hasName() || builder.hasDesc() ? builder.build() : null;
+ }
+
+ // We don't write those signatures which can be trivially reconstructed from already serialized data
+ // TODO: make JvmStringTable implement NameResolver and use JvmProtoBufUtil#getJvmMethodSignature instead
+ private boolean requiresSignature(@NotNull FunctionDescriptor descriptor, @NotNull String desc) {
+ StringBuilder sb = new StringBuilder();
+ sb.append("(");
+ ReceiverParameterDescriptor receiverParameter = descriptor.getExtensionReceiverParameter();
+ if (receiverParameter != null) {
+ String receiverDesc = mapTypeDefault(receiverParameter.getValue().getType());
+ if (receiverDesc == null) return true;
+ sb.append(receiverDesc);
+ }
+
+ for (ValueParameterDescriptor valueParameter : descriptor.getValueParameters()) {
+ String paramDesc = mapTypeDefault(valueParameter.getType());
+ if (paramDesc == null) return true;
+ sb.append(paramDesc);
+ }
+
+ sb.append(")");
+
+ JetType returnType = descriptor.getReturnType();
+ String returnTypeDesc = returnType == null ? "V" : mapTypeDefault(returnType);
+ if (returnTypeDesc == null) return true;
+ sb.append(returnTypeDesc);
+
+ return !sb.toString().equals(desc);
+ }
+
+ @Nullable
+ private String mapTypeDefault(@NotNull JetType type) {
+ ClassifierDescriptor classifier = type.getConstructor().getDeclarationDescriptor();
+ if (!(classifier instanceof ClassDescriptor)) return null;
+ ClassId classId = classId((ClassDescriptor) classifier);
+ return classId == null ? null : JvmProtoBufUtil.mapClassIdDefault(classId);
+ }
+
+ @Nullable
+ private ClassId classId(@NotNull ClassDescriptor descriptor) {
+ DeclarationDescriptor container = descriptor.getContainingDeclaration();
+ if (container instanceof PackageFragmentDescriptor) {
+ return ClassId.topLevel(((PackageFragmentDescriptor) container).getFqName().child(descriptor.getName()));
+ }
+ else if (container instanceof ClassDescriptor) {
+ ClassId outerClassId = classId((ClassDescriptor) container);
+ return outerClassId == null ? null : outerClassId.createNestedClassId(descriptor.getName());
+ }
+ else {
+ return null;
+ }
}
@NotNull
diff --git a/compiler/tests/org/jetbrains/kotlin/serialization/jvm/DebugJvmProtoBuf.java b/compiler/tests/org/jetbrains/kotlin/serialization/jvm/DebugJvmProtoBuf.java
index cb26d0e07a5..4860be4957e 100644
--- a/compiler/tests/org/jetbrains/kotlin/serialization/jvm/DebugJvmProtoBuf.java
+++ b/compiler/tests/org/jetbrains/kotlin/serialization/jvm/DebugJvmProtoBuf.java
@@ -2164,19 +2164,19 @@ public final class DebugJvmProtoBuf {
public interface JvmMethodSignatureOrBuilder
extends com.google.protobuf.MessageOrBuilder {
- // required int32 name = 1;
+ // optional int32 name = 1;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
boolean hasName();
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
int getName();
- // required int32 desc = 2;
+ // optional int32 desc = 2;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2184,7 +2184,7 @@ public final class DebugJvmProtoBuf {
*/
boolean hasDesc();
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2293,27 +2293,27 @@ public final class DebugJvmProtoBuf {
}
private int bitField0_;
- // required int32 name = 1;
+ // optional int32 name = 1;
public static final int NAME_FIELD_NUMBER = 1;
private int name_;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public boolean hasName() {
return ((bitField0_ & 0x00000001) == 0x00000001);
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public int getName() {
return name_;
}
- // required int32 desc = 2;
+ // optional int32 desc = 2;
public static final int DESC_FIELD_NUMBER = 2;
private int desc_;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2323,7 +2323,7 @@ public final class DebugJvmProtoBuf {
return ((bitField0_ & 0x00000002) == 0x00000002);
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2342,14 +2342,6 @@ public final class DebugJvmProtoBuf {
byte isInitialized = memoizedIsInitialized;
if (isInitialized != -1) return isInitialized == 1;
- if (!hasName()) {
- memoizedIsInitialized = 0;
- return false;
- }
- if (!hasDesc()) {
- memoizedIsInitialized = 0;
- return false;
- }
memoizedIsInitialized = 1;
return true;
}
@@ -2563,14 +2555,6 @@ public final class DebugJvmProtoBuf {
}
public final boolean isInitialized() {
- if (!hasName()) {
-
- return false;
- }
- if (!hasDesc()) {
-
- return false;
- }
return true;
}
@@ -2593,22 +2577,22 @@ public final class DebugJvmProtoBuf {
}
private int bitField0_;
- // required int32 name = 1;
+ // optional int32 name = 1;
private int name_ ;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public boolean hasName() {
return ((bitField0_ & 0x00000001) == 0x00000001);
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public int getName() {
return name_;
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public Builder setName(int value) {
bitField0_ |= 0x00000001;
@@ -2617,7 +2601,7 @@ public final class DebugJvmProtoBuf {
return this;
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public Builder clearName() {
bitField0_ = (bitField0_ & ~0x00000001);
@@ -2626,10 +2610,10 @@ public final class DebugJvmProtoBuf {
return this;
}
- // required int32 desc = 2;
+ // optional int32 desc = 2;
private int desc_ ;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2639,7 +2623,7 @@ public final class DebugJvmProtoBuf {
return ((bitField0_ & 0x00000002) == 0x00000002);
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2649,7 +2633,7 @@ public final class DebugJvmProtoBuf {
return desc_;
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2662,7 +2646,7 @@ public final class DebugJvmProtoBuf {
return this;
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -3663,24 +3647,6 @@ public final class DebugJvmProtoBuf {
return false;
}
}
- if (hasSyntheticMethod()) {
- if (!getSyntheticMethod().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
- if (hasGetter()) {
- if (!getGetter().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
- if (hasSetter()) {
- if (!getSetter().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
memoizedIsInitialized = 1;
return true;
}
@@ -3968,24 +3934,6 @@ public final class DebugJvmProtoBuf {
return false;
}
}
- if (hasSyntheticMethod()) {
- if (!getSyntheticMethod().isInitialized()) {
-
- return false;
- }
- }
- if (hasGetter()) {
- if (!getGetter().isInitialized()) {
-
- return false;
- }
- }
- if (hasSetter()) {
- if (!getSetter().isInitialized()) {
-
- return false;
- }
- }
return true;
}
@@ -4672,7 +4620,7 @@ public final class DebugJvmProtoBuf {
"ce_char\030\005 \003(\005B\002\020\001\"E\n\tOperation\022\010\n\004NONE\020\000" +
"\022\030\n\024INTERNAL_TO_CLASS_ID\020\001\022\024\n\020DESC_TO_CL" +
"ASS_ID\020\002\"<\n\022JvmMethodSignature\022\022\n\004name\030\001" +
- " \002(\005B\004\230\265\030\001\022\022\n\004desc\030\002 \002(\005B\004\230\265\030\001\"^\n\021JvmFie" +
+ " \001(\005B\004\230\265\030\001\022\022\n\004desc\030\002 \001(\005B\004\230\265\030\001\"^\n\021JvmFie" +
"ldSignature\022\022\n\004name\030\001 \002(\005B\004\230\265\030\001\022\022\n\004desc\030" +
"\002 \002(\005B\004\230\265\030\001\022!\n\022is_static_in_outer\030\003 \001(\010:" +
"\005false\"\316\002\n\024JvmPropertySignature\022H\n\005field",
diff --git a/core/descriptor.loader.java/src/jvm_descriptors.proto b/core/descriptor.loader.java/src/jvm_descriptors.proto
index f65226f8864..71694ebba75 100644
--- a/core/descriptor.loader.java/src/jvm_descriptors.proto
+++ b/core/descriptor.loader.java/src/jvm_descriptors.proto
@@ -62,10 +62,10 @@ message StringTableTypes {
}
message JvmMethodSignature {
- required int32 name = 1 [(string_id_in_table) = true];
+ optional int32 name = 1 [(string_id_in_table) = true];
// JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
- required int32 desc = 2 [(string_id_in_table) = true];
+ optional int32 desc = 2 [(string_id_in_table) = true];
}
message JvmFieldSignature {
diff --git a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/AbstractBinaryClassAnnotationAndConstantLoader.kt b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/AbstractBinaryClassAnnotationAndConstantLoader.kt
index 6e0045b2922..2e4b7874bb9 100644
--- a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/AbstractBinaryClassAnnotationAndConstantLoader.kt
+++ b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/AbstractBinaryClassAnnotationAndConstantLoader.kt
@@ -24,7 +24,11 @@ import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.*
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf
-import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf.*
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf.index
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf.methodImplClassName
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf.propertyImplClassName
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf.propertySignature
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBufUtil
import org.jetbrains.kotlin.storage.StorageManager
import org.jetbrains.kotlin.types.JetType
import java.util.*
@@ -297,11 +301,11 @@ public abstract class AbstractBinaryClassAnnotationAndConstantLoader {
- MemberSignature.fromMethod(nameResolver, proto.getExtension(constructorSignature))
+ proto is ProtoBuf.Constructor -> {
+ MemberSignature.fromMethodNameAndDesc(JvmProtoBufUtil.getJvmConstructorSignature(proto, nameResolver) ?: return null)
}
- proto is ProtoBuf.Function && proto.hasExtension(methodSignature) -> {
- MemberSignature.fromMethod(nameResolver, proto.getExtension(methodSignature))
+ proto is ProtoBuf.Function -> {
+ MemberSignature.fromMethodNameAndDesc(JvmProtoBufUtil.getJvmMethodSignature(proto, nameResolver) ?: return null)
}
proto is ProtoBuf.Property && proto.hasExtension(propertySignature) -> {
val signature = proto.getExtension(propertySignature)
diff --git a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/MemberSignature.kt b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/MemberSignature.kt
index 83a7240755f..b6e976ee7f3 100644
--- a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/MemberSignature.kt
+++ b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/kotlin/MemberSignature.kt
@@ -33,6 +33,11 @@ data class MemberSignature private constructor(private val signature: String) {
return MemberSignature(name + desc)
}
+ @JvmStatic
+ public fun fromMethodNameAndDesc(namePlusDesc: String): MemberSignature {
+ return MemberSignature(namePlusDesc)
+ }
+
@JvmStatic
public fun fromFieldNameAndDesc(name: String, desc: String): MemberSignature {
return MemberSignature(name + "#" + desc)
diff --git a/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBuf.java b/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBuf.java
index ca8ca511abd..672d4e959cd 100644
--- a/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBuf.java
+++ b/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBuf.java
@@ -1860,19 +1860,19 @@ public final class JvmProtoBuf {
public interface JvmMethodSignatureOrBuilder
extends com.google.protobuf.MessageLiteOrBuilder {
- // required int32 name = 1;
+ // optional int32 name = 1;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
boolean hasName();
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
int getName();
- // required int32 desc = 2;
+ // optional int32 desc = 2;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -1880,7 +1880,7 @@ public final class JvmProtoBuf {
*/
boolean hasDesc();
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -1968,27 +1968,27 @@ public final class JvmProtoBuf {
}
private int bitField0_;
- // required int32 name = 1;
+ // optional int32 name = 1;
public static final int NAME_FIELD_NUMBER = 1;
private int name_;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public boolean hasName() {
return ((bitField0_ & 0x00000001) == 0x00000001);
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public int getName() {
return name_;
}
- // required int32 desc = 2;
+ // optional int32 desc = 2;
public static final int DESC_FIELD_NUMBER = 2;
private int desc_;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -1998,7 +1998,7 @@ public final class JvmProtoBuf {
return ((bitField0_ & 0x00000002) == 0x00000002);
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2017,14 +2017,6 @@ public final class JvmProtoBuf {
byte isInitialized = memoizedIsInitialized;
if (isInitialized != -1) return isInitialized == 1;
- if (!hasName()) {
- memoizedIsInitialized = 0;
- return false;
- }
- if (!hasDesc()) {
- memoizedIsInitialized = 0;
- return false;
- }
memoizedIsInitialized = 1;
return true;
}
@@ -2196,14 +2188,6 @@ public final class JvmProtoBuf {
}
public final boolean isInitialized() {
- if (!hasName()) {
-
- return false;
- }
- if (!hasDesc()) {
-
- return false;
- }
return true;
}
@@ -2226,22 +2210,22 @@ public final class JvmProtoBuf {
}
private int bitField0_;
- // required int32 name = 1;
+ // optional int32 name = 1;
private int name_ ;
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public boolean hasName() {
return ((bitField0_ & 0x00000001) == 0x00000001);
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public int getName() {
return name_;
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public Builder setName(int value) {
bitField0_ |= 0x00000001;
@@ -2250,7 +2234,7 @@ public final class JvmProtoBuf {
return this;
}
/**
- * required int32 name = 1;
+ * optional int32 name = 1;
*/
public Builder clearName() {
bitField0_ = (bitField0_ & ~0x00000001);
@@ -2259,10 +2243,10 @@ public final class JvmProtoBuf {
return this;
}
- // required int32 desc = 2;
+ // optional int32 desc = 2;
private int desc_ ;
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2272,7 +2256,7 @@ public final class JvmProtoBuf {
return ((bitField0_ & 0x00000002) == 0x00000002);
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2282,7 +2266,7 @@ public final class JvmProtoBuf {
return desc_;
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -2295,7 +2279,7 @@ public final class JvmProtoBuf {
return this;
}
/**
- * required int32 desc = 2;
+ * optional int32 desc = 2;
*
*
* JVM descriptor of the method, e.g. '(Ljava/util/List;)[Ljava/lang/Object;'
@@ -3164,24 +3148,6 @@ public final class JvmProtoBuf {
return false;
}
}
- if (hasSyntheticMethod()) {
- if (!getSyntheticMethod().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
- if (hasGetter()) {
- if (!getGetter().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
- if (hasSetter()) {
- if (!getSetter().isInitialized()) {
- memoizedIsInitialized = 0;
- return false;
- }
- }
memoizedIsInitialized = 1;
return true;
}
@@ -3391,24 +3357,6 @@ public final class JvmProtoBuf {
return false;
}
}
- if (hasSyntheticMethod()) {
- if (!getSyntheticMethod().isInitialized()) {
-
- return false;
- }
- }
- if (hasGetter()) {
- if (!getGetter().isInitialized()) {
-
- return false;
- }
- }
- if (hasSetter()) {
- if (!getSetter().isInitialized()) {
-
- return false;
- }
- }
return true;
}
diff --git a/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBufUtil.kt b/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBufUtil.kt
index f62a1bd7065..7f261c7ca8e 100644
--- a/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBufUtil.kt
+++ b/core/descriptor.loader.java/src/org/jetbrains/kotlin/serialization/jvm/JvmProtoBufUtil.kt
@@ -17,10 +17,15 @@
package org.jetbrains.kotlin.serialization.jvm
import com.google.protobuf.ExtensionRegistryLite
+import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.load.kotlin.JvmNameResolver
+import org.jetbrains.kotlin.name.ClassId
+import org.jetbrains.kotlin.platform.JavaToKotlinClassMap
+import org.jetbrains.kotlin.resolve.jvm.JvmPrimitiveType
import org.jetbrains.kotlin.serialization.ClassData
import org.jetbrains.kotlin.serialization.PackageData
import org.jetbrains.kotlin.serialization.ProtoBuf
+import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import java.io.ByteArrayInputStream
public object JvmProtoBufUtil {
@@ -53,4 +58,64 @@ public object JvmProtoBufUtil {
val packageProto = ProtoBuf.Package.parseFrom(input, EXTENSION_REGISTRY)
return PackageData(nameResolver, packageProto)
}
+
+ // returns JVM signature in the format: "equals(Ljava/lang/Object;)Z"
+ fun getJvmMethodSignature(proto: ProtoBuf.FunctionOrBuilder, nameResolver: NameResolver): String? {
+ val signature =
+ if (proto.hasExtension(JvmProtoBuf.methodSignature)) proto.getExtension(JvmProtoBuf.methodSignature) else null
+ val name = if (signature != null && signature.hasName()) signature.name else proto.name
+ val desc = if (signature != null && signature.hasDesc()) {
+ nameResolver.getString(signature.desc)
+ }
+ else {
+ val parameterTypes =
+ (if (proto.hasReceiverType()) listOf(proto.receiverType) else listOf()) + proto.valueParameterList.map { it.type }
+
+ val parametersDesc = parameterTypes.map { mapTypeDefault(it, nameResolver) ?: return null }
+ val returnTypeDesc = mapTypeDefault(proto.returnType, nameResolver) ?: return null
+
+ parametersDesc.joinToString(separator = "", prefix = "(", postfix = ")") + returnTypeDesc
+ }
+ return nameResolver.getString(name) + desc
+ }
+
+ fun getJvmConstructorSignature(proto: ProtoBuf.ConstructorOrBuilder, nameResolver: NameResolver): String? {
+ val signature =
+ if (proto.hasExtension(JvmProtoBuf.constructorSignature)) proto.getExtension(JvmProtoBuf.constructorSignature) else null
+ val desc = if (signature != null && signature.hasDesc()) {
+ nameResolver.getString(signature.desc)
+ }
+ else {
+ proto.valueParameterList.map {
+ mapTypeDefault(it.type, nameResolver) ?: return null
+ }.joinToString(separator = "", prefix = "(", postfix = ")V")
+ }
+ return "" + desc
+ }
+
+ private fun mapTypeDefault(type: ProtoBuf.Type, nameResolver: NameResolver): String? {
+ return if (type.hasClassName()) mapClassIdDefault(nameResolver.getClassId(type.className)) else null
+ }
+
+ @JvmStatic
+ fun mapClassIdDefault(classId: ClassId): String {
+ val internalName = classId.asString().replace('.', '$')
+ val simpleName = internalName.removePrefix("kotlin/")
+ if (simpleName != internalName) {
+ for (jvmPrimitive in JvmPrimitiveType.values()) {
+ val primitiveType = jvmPrimitive.primitiveType
+ if (simpleName == primitiveType.typeName.asString()) return jvmPrimitive.desc
+ if (simpleName == primitiveType.arrayTypeName.asString()) return "[" + jvmPrimitive.desc
+ }
+
+ if (simpleName == KotlinBuiltIns.FQ_NAMES.unit.shortName().asString()) return "V"
+ }
+
+ val javaClassId = JavaToKotlinClassMap.INSTANCE.mapKotlinToJava(classId.asSingleFqName().toUnsafe())
+ if (javaClassId != null) {
+ return "L" + javaClassId.asString().replace('.', '$') + ";"
+ }
+
+ return "L$internalName;"
+ }
}
diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KDeclarationContainerImpl.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KDeclarationContainerImpl.kt
index 9c9d3944683..a56d38f39cb 100644
--- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KDeclarationContainerImpl.kt
+++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KDeclarationContainerImpl.kt
@@ -156,79 +156,49 @@ internal abstract class KDeclarationContainerImpl : ClassBasedDeclarationContain
}
// TODO: check resulting method's return type
- fun findMethodBySignature(
- signature: JvmProtoBuf.JvmMethodSignature,
- nameResolver: NameResolver,
- declared: Boolean
- ): Method? {
- val name = nameResolver.getString(signature.name)
+ fun findMethodBySignature(name: String, desc: String, declared: Boolean): Method? {
if (name == "") return null
- val parameterTypes = loadParameterTypes(nameResolver, signature)
-
// Method for a top level function should be the one from the package facade.
// This is likely to change after the package part reform.
- val owner = jClass
-
- return owner.tryGetMethod(name, parameterTypes, declared)
+ return jClass.tryGetMethod(name, loadParameterTypes(desc), declared)
}
- fun findDefaultMethod(
- signature: JvmProtoBuf.JvmMethodSignature,
- nameResolver: NameResolver,
- isMember: Boolean,
- declared: Boolean
- ): Method? {
- val name = nameResolver.getString(signature.name)
+ fun findDefaultMethod(name: String, desc: String, isMember: Boolean, declared: Boolean): Method? {
if (name == "") return null
val parameterTypes = arrayListOf>()
if (isMember) {
parameterTypes.add(jClass)
}
- addParametersAndMasks(parameterTypes, nameResolver, signature)
+ addParametersAndMasks(parameterTypes, desc)
return jClass.tryGetMethod(name + JvmAbi.DEFAULT_PARAMS_IMPL_SUFFIX, parameterTypes, declared)
}
- fun findConstructorBySignature(
- signature: JvmProtoBuf.JvmMethodSignature,
- nameResolver: NameResolver,
- declared: Boolean
- ): Constructor<*>? {
- if (nameResolver.getString(signature.name) != "") return null
-
- return jClass.tryGetConstructor(loadParameterTypes(nameResolver, signature), declared)
+ fun findConstructorBySignature(desc: String, declared: Boolean): Constructor<*>? {
+ return jClass.tryGetConstructor(loadParameterTypes(desc), declared)
}
- fun findDefaultConstructor(
- signature: JvmProtoBuf.JvmMethodSignature,
- nameResolver: NameResolver,
- declared: Boolean
- ): Constructor<*>? {
- if (nameResolver.getString(signature.name) != "") return null
-
+ fun findDefaultConstructor(desc: String, declared: Boolean): Constructor<*>? {
val parameterTypes = arrayListOf>()
- addParametersAndMasks(parameterTypes, nameResolver, signature)
+ addParametersAndMasks(parameterTypes, desc)
parameterTypes.add(DEFAULT_CONSTRUCTOR_MARKER)
return jClass.tryGetConstructor(parameterTypes, declared)
}
- private fun addParametersAndMasks(
- result: MutableList>, nameResolver: NameResolver, signature: JvmProtoBuf.JvmMethodSignature
- ) {
- val valueParameters = loadParameterTypes(nameResolver, signature)
+ private fun addParametersAndMasks(result: MutableList>, desc: String) {
+ val valueParameters = loadParameterTypes(desc)
result.addAll(valueParameters)
repeat((valueParameters.size() + Integer.SIZE - 1) / Integer.SIZE) {
result.add(Integer.TYPE)
}
}
- private fun loadParameterTypes(nameResolver: NameResolver, signature: JvmProtoBuf.JvmMethodSignature): List> {
+ private fun loadParameterTypes(desc: String): List> {
val classLoader = jClass.safeClassLoader
val result = arrayListOf>()
- val desc = nameResolver.getString(signature.desc)
var i = 1
while (desc[i] != ')') {
diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KFunctionImpl.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KFunctionImpl.kt
index 494658c07a4..c6698c860d4 100644
--- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KFunctionImpl.kt
+++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KFunctionImpl.kt
@@ -51,8 +51,8 @@ internal open class KFunctionImpl protected constructor(
override val caller: FunctionCaller<*> by ReflectProperties.lazySoft {
val jvmSignature = RuntimeTypeMapper.mapSignature(descriptor)
val member: Member? = when (jvmSignature) {
- is KotlinConstructor -> container.findConstructorBySignature(jvmSignature.signature, jvmSignature.nameResolver, isDeclared())
- is KotlinFunction -> container.findMethodBySignature(jvmSignature.signature, jvmSignature.nameResolver, isDeclared())
+ is KotlinConstructor -> container.findConstructorBySignature(jvmSignature.constructorDesc, isDeclared())
+ is KotlinFunction -> container.findMethodBySignature(jvmSignature.methodName, jvmSignature.methodDesc, isDeclared())
is JavaMethod -> jvmSignature.method
is JavaConstructor -> jvmSignature.constructor
is BuiltInFunction -> jvmSignature.getMember(container)
@@ -76,11 +76,11 @@ internal open class KFunctionImpl protected constructor(
val jvmSignature = RuntimeTypeMapper.mapSignature(descriptor)
val member: Member? = when (jvmSignature) {
is KotlinFunction -> {
- container.findDefaultMethod(jvmSignature.signature, jvmSignature.nameResolver,
+ container.findDefaultMethod(jvmSignature.methodName, jvmSignature.methodDesc,
!Modifier.isStatic(caller.member.modifiers), isDeclared())
}
is KotlinConstructor -> {
- container.findDefaultConstructor(jvmSignature.signature, jvmSignature.nameResolver, isDeclared())
+ container.findDefaultConstructor(jvmSignature.constructorDesc, isDeclared())
}
else -> {
// Java methods, Java constructors and built-ins don't have $default methods
diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KPropertyImpl.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KPropertyImpl.kt
index ededc1c41fc..1070937fd6e 100644
--- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KPropertyImpl.kt
+++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KPropertyImpl.kt
@@ -116,7 +116,11 @@ private fun KPropertyImpl.Accessor<*>.computeCallerForAccessor(isGetter: Boolean
}
val accessor = accessorSignature?.let { signature ->
- property.container.findMethodBySignature(signature, jvmSignature.nameResolver, Visibilities.isPrivate(descriptor.visibility))
+ property.container.findMethodBySignature(
+ jvmSignature.nameResolver.getString(signature.name),
+ jvmSignature.nameResolver.getString(signature.desc),
+ Visibilities.isPrivate(descriptor.visibility)
+ )
}
when {
diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/RuntimeTypeMapper.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/RuntimeTypeMapper.kt
index 5b071695bca..3dd5ae12754 100644
--- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/RuntimeTypeMapper.kt
+++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/RuntimeTypeMapper.kt
@@ -36,6 +36,7 @@ import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedCallableMemberDescriptor
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedPropertyDescriptor
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf
+import org.jetbrains.kotlin.serialization.jvm.JvmProtoBufUtil
import java.lang.reflect.Constructor
import java.lang.reflect.Field
import java.lang.reflect.Member
@@ -45,22 +46,17 @@ import kotlin.reflect.KotlinReflectionInternalError
internal sealed class JvmFunctionSignature {
abstract fun asString(): String
- class KotlinFunction(
- val proto: ProtoBuf.Function,
- val signature: JvmProtoBuf.JvmMethodSignature,
- val nameResolver: NameResolver
- ) : JvmFunctionSignature() {
- override fun asString(): String =
- nameResolver.getString(signature.name) + nameResolver.getString(signature.desc)
+ class KotlinFunction(val signature: String) : JvmFunctionSignature() {
+ val methodName: String get() = signature.substringBefore('(')
+ val methodDesc: String get() = signature.substring(signature.indexOf('('))
+
+ override fun asString(): String = signature
}
- class KotlinConstructor(
- val proto: ProtoBuf.Constructor,
- val signature: JvmProtoBuf.JvmMethodSignature,
- val nameResolver: NameResolver
- ) : JvmFunctionSignature() {
- override fun asString(): String =
- nameResolver.getString(signature.name) + nameResolver.getString(signature.desc)
+ class KotlinConstructor(val signature: String) : JvmFunctionSignature() {
+ val constructorDesc: String get() = signature.substring(signature.indexOf('('))
+
+ override fun asString(): String = signature
}
class JavaMethod(val method: Method) : JvmFunctionSignature() {
@@ -132,19 +128,24 @@ internal object RuntimeTypeMapper {
when (function) {
is DeserializedCallableMemberDescriptor -> {
- val proto = function.proto
- if (proto is ProtoBuf.Function && proto.hasExtension(JvmProtoBuf.methodSignature)) {
- val signature = proto.getExtension(JvmProtoBuf.methodSignature)
- return JvmFunctionSignature.KotlinFunction(proto, signature, function.nameResolver)
+ mapIntrinsicFunctionSignature(function)?.let {
+ return it
}
- if (proto is ProtoBuf.Constructor && proto.hasExtension(JvmProtoBuf.constructorSignature)) {
- val signature = proto.getExtension(JvmProtoBuf.constructorSignature)
- return JvmFunctionSignature.KotlinConstructor(proto, signature, function.nameResolver)
+
+ val proto = function.proto
+ if (proto is ProtoBuf.Function) {
+ JvmProtoBufUtil.getJvmMethodSignature(proto, function.nameResolver)?.let { signature ->
+ return JvmFunctionSignature.KotlinFunction(signature)
+ }
+ }
+ if (proto is ProtoBuf.Constructor) {
+ JvmProtoBufUtil.getJvmConstructorSignature(proto, function.nameResolver)?.let { signature ->
+ return JvmFunctionSignature.KotlinConstructor(signature)
+ }
}
// If it's a deserialized function but has no JVM signature, it must be from built-ins
- return mapIntrinsicFunctionSignature(function) ?:
- throw KotlinReflectionInternalError("Reflection on built-in Kotlin types is not yet fully supported. " +
- "No metadata found for $function")
+ throw KotlinReflectionInternalError("Reflection on built-in Kotlin types is not yet fully supported. " +
+ "No metadata found for $function")
}
is JavaMethodDescriptor -> {
val method = ((function.source as? JavaSourceElement)?.javaElement as? ReflectJavaMethod)?.member ?:
diff --git a/jps-plugin/src/org/jetbrains/kotlin/jps/incremental/ProtoCompareGenerated.kt b/jps-plugin/src/org/jetbrains/kotlin/jps/incremental/ProtoCompareGenerated.kt
index da4adbf258f..fb2c9754a14 100644
--- a/jps-plugin/src/org/jetbrains/kotlin/jps/incremental/ProtoCompareGenerated.kt
+++ b/jps-plugin/src/org/jetbrains/kotlin/jps/incremental/ProtoCompareGenerated.kt
@@ -330,9 +330,15 @@ open class ProtoCompareGenerated(public val oldNameResolver: NameResolver, publi
}
open fun checkEquals(old: JvmProtoBuf.JvmMethodSignature, new: JvmProtoBuf.JvmMethodSignature): Boolean {
- if (!checkStringEquals(old.name, new.name)) return false
+ if (old.hasName() != new.hasName()) return false
+ if (old.hasName()) {
+ if (!checkStringEquals(old.name, new.name)) return false
+ }
- if (!checkStringEquals(old.desc, new.desc)) return false
+ if (old.hasDesc() != new.hasDesc()) return false
+ if (old.hasDesc()) {
+ if (!checkStringEquals(old.desc, new.desc)) return false
+ }
return true
}
@@ -896,9 +902,13 @@ public fun ProtoBuf.ValueParameter.hashCode(stringIndexes: (Int) -> Int, fqNameI
public fun JvmProtoBuf.JvmMethodSignature.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
- hashCode = 31 * hashCode + stringIndexes(name)
+ if (hasName()) {
+ hashCode = 31 * hashCode + stringIndexes(name)
+ }
- hashCode = 31 * hashCode + stringIndexes(desc)
+ if (hasDesc()) {
+ hashCode = 31 * hashCode + stringIndexes(desc)
+ }
return hashCode
}