Simplify ImplementationBodyCodegen#generateToArray
- don't do anything for interfaces because there's no point in generating abstract methods which are already abstract in supertypes - don't use getDeclaredFunctionByRawSignature, check function signature manually instead - don't use isOrOverridesSynthesized because 'toArray' is never synthesized
This commit is contained in:
@@ -49,7 +49,6 @@ import org.jetbrains.kotlin.psi.*;
|
|||||||
import org.jetbrains.kotlin.resolve.BindingContext;
|
import org.jetbrains.kotlin.resolve.BindingContext;
|
||||||
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils;
|
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils;
|
||||||
import org.jetbrains.kotlin.resolve.DescriptorUtils;
|
import org.jetbrains.kotlin.resolve.DescriptorUtils;
|
||||||
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.CallResolverUtilKt;
|
|
||||||
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilKt;
|
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilKt;
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.DefaultValueArgument;
|
import org.jetbrains.kotlin.resolve.calls.model.DefaultValueArgument;
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.ExpressionValueArgument;
|
import org.jetbrains.kotlin.resolve.calls.model.ExpressionValueArgument;
|
||||||
@@ -411,72 +410,78 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isGenericToArrayPresent() {
|
private boolean isGenericToArray(@NotNull FunctionDescriptor function) {
|
||||||
Collection<SimpleFunctionDescriptor> functions =
|
if (function.getValueParameters().size() != 1 || function.getTypeParameters().size() != 1) {
|
||||||
descriptor.getDefaultType().getMemberScope().getContributedFunctions(Name.identifier("toArray"), NoLookupLocation.FROM_BACKEND);
|
return false;
|
||||||
for (FunctionDescriptor function : functions) {
|
}
|
||||||
if (CallResolverUtilKt.isOrOverridesSynthesized(function)) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (function.getValueParameters().size() != 1 || function.getTypeParameters().size() != 1) {
|
KotlinType returnType = function.getReturnType();
|
||||||
continue;
|
assert returnType != null : function.toString();
|
||||||
}
|
KotlinType paramType = function.getValueParameters().get(0).getType();
|
||||||
|
if (KotlinBuiltIns.isArray(returnType) && KotlinBuiltIns.isArray(paramType)) {
|
||||||
KotlinType returnType = function.getReturnType();
|
KotlinType elementType = function.getTypeParameters().get(0).getDefaultType();
|
||||||
assert returnType != null : function.toString();
|
KotlinBuiltIns builtIns = DescriptorUtilsKt.getBuiltIns(descriptor);
|
||||||
KotlinType paramType = function.getValueParameters().get(0).getType();
|
if (KotlinTypeChecker.DEFAULT.equalTypes(elementType, builtIns.getArrayElementType(returnType))
|
||||||
if (KotlinBuiltIns.isArray(returnType) && KotlinBuiltIns.isArray(paramType)) {
|
&& KotlinTypeChecker.DEFAULT.equalTypes(elementType, builtIns.getArrayElementType(paramType))) {
|
||||||
KotlinType elementType = function.getTypeParameters().get(0).getDefaultType();
|
return true;
|
||||||
if (KotlinTypeChecker.DEFAULT.equalTypes(elementType, DescriptorUtilsKt.getBuiltIns(descriptor).getArrayElementType(returnType))
|
|
||||||
&& KotlinTypeChecker.DEFAULT.equalTypes(elementType, DescriptorUtilsKt
|
|
||||||
.getBuiltIns(descriptor).getArrayElementType(paramType))) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static boolean isNonGenericToArray(@NotNull FunctionDescriptor function) {
|
||||||
|
if (!function.getValueParameters().isEmpty() || !function.getTypeParameters().isEmpty()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
KotlinType returnType = function.getReturnType();
|
||||||
|
return returnType != null && KotlinBuiltIns.isArray(returnType);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void generateToArray() {
|
private void generateToArray() {
|
||||||
|
if (descriptor.getKind() == ClassKind.INTERFACE) return;
|
||||||
|
|
||||||
KotlinBuiltIns builtIns = DescriptorUtilsKt.getBuiltIns(descriptor);
|
KotlinBuiltIns builtIns = DescriptorUtilsKt.getBuiltIns(descriptor);
|
||||||
if (!isSubclass(descriptor, builtIns.getCollection())) return;
|
if (!isSubclass(descriptor, builtIns.getCollection())) return;
|
||||||
|
|
||||||
int access = descriptor.getKind() == ClassKind.INTERFACE ?
|
Collection<SimpleFunctionDescriptor> functions = descriptor.getDefaultType().getMemberScope().getContributedFunctions(
|
||||||
ACC_PUBLIC | ACC_ABSTRACT :
|
Name.identifier("toArray"), NoLookupLocation.FROM_BACKEND
|
||||||
ACC_PUBLIC;
|
);
|
||||||
if (CodegenUtil.getDeclaredFunctionByRawSignature(descriptor, Name.identifier("toArray"), builtIns.getArray()) == null) {
|
boolean hasGenericToArray = false;
|
||||||
MethodVisitor mv = v.newMethod(NO_ORIGIN, access, "toArray", "()[Ljava/lang/Object;", null, null);
|
boolean hasNonGenericToArray = false;
|
||||||
|
for (FunctionDescriptor function : functions) {
|
||||||
if (descriptor.getKind() != ClassKind.INTERFACE) {
|
hasGenericToArray |= isGenericToArray(function);
|
||||||
InstructionAdapter iv = new InstructionAdapter(mv);
|
hasNonGenericToArray |= isNonGenericToArray(function);
|
||||||
mv.visitCode();
|
|
||||||
|
|
||||||
iv.load(0, classAsmType);
|
|
||||||
iv.invokestatic("kotlin/jvm/internal/CollectionToArray", "toArray", "(Ljava/util/Collection;)[Ljava/lang/Object;", false);
|
|
||||||
iv.areturn(Type.getType("[Ljava/lang/Object;"));
|
|
||||||
|
|
||||||
FunctionCodegen.endVisit(mv, "toArray", myClass);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isGenericToArrayPresent()) {
|
if (!hasNonGenericToArray) {
|
||||||
MethodVisitor mv = v.newMethod(NO_ORIGIN, access, "toArray", "([Ljava/lang/Object;)[Ljava/lang/Object;", null, null);
|
MethodVisitor mv = v.newMethod(NO_ORIGIN, ACC_PUBLIC, "toArray", "()[Ljava/lang/Object;", null, null);
|
||||||
|
|
||||||
if (descriptor.getKind() != ClassKind.INTERFACE) {
|
InstructionAdapter iv = new InstructionAdapter(mv);
|
||||||
InstructionAdapter iv = new InstructionAdapter(mv);
|
mv.visitCode();
|
||||||
mv.visitCode();
|
|
||||||
|
|
||||||
iv.load(0, classAsmType);
|
iv.load(0, classAsmType);
|
||||||
iv.load(1, Type.getType("[Ljava/lang/Object;"));
|
iv.invokestatic("kotlin/jvm/internal/CollectionToArray", "toArray", "(Ljava/util/Collection;)[Ljava/lang/Object;", false);
|
||||||
|
iv.areturn(Type.getType("[Ljava/lang/Object;"));
|
||||||
|
|
||||||
iv.invokestatic("kotlin/jvm/internal/CollectionToArray", "toArray",
|
FunctionCodegen.endVisit(mv, "toArray", myClass);
|
||||||
"(Ljava/util/Collection;[Ljava/lang/Object;)[Ljava/lang/Object;", false);
|
}
|
||||||
iv.areturn(Type.getType("[Ljava/lang/Object;"));
|
|
||||||
|
|
||||||
FunctionCodegen.endVisit(mv, "toArray", myClass);
|
if (!hasGenericToArray) {
|
||||||
}
|
MethodVisitor mv = v.newMethod(NO_ORIGIN, ACC_PUBLIC, "toArray", "([Ljava/lang/Object;)[Ljava/lang/Object;", null, null);
|
||||||
|
|
||||||
|
InstructionAdapter iv = new InstructionAdapter(mv);
|
||||||
|
mv.visitCode();
|
||||||
|
|
||||||
|
iv.load(0, classAsmType);
|
||||||
|
iv.load(1, Type.getType("[Ljava/lang/Object;"));
|
||||||
|
|
||||||
|
iv.invokestatic("kotlin/jvm/internal/CollectionToArray", "toArray",
|
||||||
|
"(Ljava/util/Collection;[Ljava/lang/Object;)[Ljava/lang/Object;", false);
|
||||||
|
iv.areturn(Type.getType("[Ljava/lang/Object;"));
|
||||||
|
|
||||||
|
FunctionCodegen.endVisit(mv, "toArray", myClass);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -122,8 +122,6 @@ public interface I1 {
|
|||||||
inner class I1$DefaultImpls
|
inner class I1$DefaultImpls
|
||||||
public abstract method contains(p0: java.lang.Object): boolean
|
public abstract method contains(p0: java.lang.Object): boolean
|
||||||
public abstract method containsAll(@org.jetbrains.annotations.NotNull p0: java.util.Collection): boolean
|
public abstract method containsAll(@org.jetbrains.annotations.NotNull p0: java.util.Collection): boolean
|
||||||
public abstract method toArray(): java.lang.Object[]
|
|
||||||
public abstract method toArray(p0: java.lang.Object[]): java.lang.Object[]
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@kotlin.Metadata
|
@kotlin.Metadata
|
||||||
@@ -138,6 +136,4 @@ public interface I2 {
|
|||||||
inner class I2$DefaultImpls
|
inner class I2$DefaultImpls
|
||||||
public abstract method contains(@org.jetbrains.annotations.NotNull p0: java.lang.String): boolean
|
public abstract method contains(@org.jetbrains.annotations.NotNull p0: java.lang.String): boolean
|
||||||
public abstract method containsAll(@org.jetbrains.annotations.NotNull p0: java.util.Collection): boolean
|
public abstract method containsAll(@org.jetbrains.annotations.NotNull p0: java.util.Collection): boolean
|
||||||
public abstract method toArray(): java.lang.Object[]
|
|
||||||
public abstract method toArray(p0: java.lang.Object[]): java.lang.Object[]
|
|
||||||
}
|
}
|
||||||
@@ -2089,8 +2089,6 @@ public abstract interface class kotlin/text/MatchGroupCollection : java/util/Col
|
|||||||
public abstract fun remove (Lkotlin/text/MatchGroup;)Z
|
public abstract fun remove (Lkotlin/text/MatchGroup;)Z
|
||||||
public abstract fun removeAll (Ljava/util/Collection;)Z
|
public abstract fun removeAll (Ljava/util/Collection;)Z
|
||||||
public abstract fun retainAll (Ljava/util/Collection;)Z
|
public abstract fun retainAll (Ljava/util/Collection;)Z
|
||||||
public abstract fun toArray ()[Ljava/lang/Object;
|
|
||||||
public abstract fun toArray ([Ljava/lang/Object;)[Ljava/lang/Object;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public abstract interface class kotlin/text/MatchResult {
|
public abstract interface class kotlin/text/MatchResult {
|
||||||
|
|||||||
Reference in New Issue
Block a user