extract getTraitMethods from ImplementationBodyGen to CodegenUtil
This commit is contained in:
@@ -18,6 +18,7 @@ package org.jetbrains.jet.backend.common;
|
|||||||
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
import org.jetbrains.jet.codegen.bridges.BridgesPackage;
|
||||||
import org.jetbrains.jet.lang.descriptors.*;
|
import org.jetbrains.jet.lang.descriptors.*;
|
||||||
import org.jetbrains.jet.lang.psi.JetDelegationSpecifier;
|
import org.jetbrains.jet.lang.psi.JetDelegationSpecifier;
|
||||||
import org.jetbrains.jet.lang.psi.JetExpression;
|
import org.jetbrains.jet.lang.psi.JetExpression;
|
||||||
@@ -145,6 +146,40 @@ public class CodegenUtil {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public static Map<FunctionDescriptor, FunctionDescriptor> getTraitMethods(ClassDescriptor descriptor) {
|
||||||
|
Map<FunctionDescriptor, FunctionDescriptor> result = new LinkedHashMap<FunctionDescriptor, FunctionDescriptor>();
|
||||||
|
for (DeclarationDescriptor declaration : descriptor.getDefaultType().getMemberScope().getAllDescriptors()) {
|
||||||
|
if (!(declaration instanceof CallableMemberDescriptor)) continue;
|
||||||
|
|
||||||
|
CallableMemberDescriptor inheritedMember = (CallableMemberDescriptor) declaration;
|
||||||
|
CallableMemberDescriptor traitMember = BridgesPackage.findTraitImplementation(inheritedMember);
|
||||||
|
if (traitMember == null) continue;
|
||||||
|
|
||||||
|
assert traitMember.getModality() != Modality.ABSTRACT : "Cannot delegate to abstract trait method: " + inheritedMember;
|
||||||
|
|
||||||
|
// inheritedMember can be abstract here. In order for FunctionCodegen to generate the method body, we're creating a copy here
|
||||||
|
// with traitMember's modality
|
||||||
|
CallableMemberDescriptor copy =
|
||||||
|
inheritedMember.copy(inheritedMember.getContainingDeclaration(), traitMember.getModality(), Visibilities.PUBLIC,
|
||||||
|
CallableMemberDescriptor.Kind.DECLARATION, true);
|
||||||
|
|
||||||
|
if (traitMember instanceof SimpleFunctionDescriptor) {
|
||||||
|
result.put((FunctionDescriptor) traitMember, (FunctionDescriptor) copy);
|
||||||
|
}
|
||||||
|
else if (traitMember instanceof PropertyDescriptor) {
|
||||||
|
for (PropertyAccessorDescriptor traitAccessor : ((PropertyDescriptor) traitMember).getAccessors()) {
|
||||||
|
for (PropertyAccessorDescriptor inheritedAccessor : ((PropertyDescriptor) copy).getAccessors()) {
|
||||||
|
if (inheritedAccessor.getClass() == traitAccessor.getClass()) { // same accessor kind
|
||||||
|
result.put(traitAccessor, inheritedAccessor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static ClassDescriptor getSuperClassByDelegationSpecifier(@NotNull JetDelegationSpecifier specifier, @NotNull BindingContext bindingContext) {
|
public static ClassDescriptor getSuperClassByDelegationSpecifier(@NotNull JetDelegationSpecifier specifier, @NotNull BindingContext bindingContext) {
|
||||||
JetType superType = bindingContext.get(BindingContext.TYPE, specifier.getTypeReference());
|
JetType superType = bindingContext.get(BindingContext.TYPE, specifier.getTypeReference());
|
||||||
|
|||||||
@@ -26,7 +26,6 @@ import org.jetbrains.annotations.Nullable;
|
|||||||
import org.jetbrains.jet.backend.common.CodegenUtil;
|
import org.jetbrains.jet.backend.common.CodegenUtil;
|
||||||
import org.jetbrains.jet.backend.common.DataClassMethodGenerator;
|
import org.jetbrains.jet.backend.common.DataClassMethodGenerator;
|
||||||
import org.jetbrains.jet.codegen.binding.MutableClosure;
|
import org.jetbrains.jet.codegen.binding.MutableClosure;
|
||||||
import org.jetbrains.jet.codegen.bridges.BridgesPackage;
|
|
||||||
import org.jetbrains.jet.codegen.context.*;
|
import org.jetbrains.jet.codegen.context.*;
|
||||||
import org.jetbrains.jet.codegen.signature.BothSignatureWriter;
|
import org.jetbrains.jet.codegen.signature.BothSignatureWriter;
|
||||||
import org.jetbrains.jet.codegen.state.GenerationState;
|
import org.jetbrains.jet.codegen.state.GenerationState;
|
||||||
@@ -1409,33 +1408,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
|
|||||||
private void generateTraitMethods() {
|
private void generateTraitMethods() {
|
||||||
if (JetPsiUtil.isTrait(myClass)) return;
|
if (JetPsiUtil.isTrait(myClass)) return;
|
||||||
|
|
||||||
for (DeclarationDescriptor declaration : descriptor.getDefaultType().getMemberScope().getAllDescriptors()) {
|
for(Map.Entry<FunctionDescriptor, FunctionDescriptor> entry : CodegenUtil.getTraitMethods(descriptor).entrySet()) {
|
||||||
if (!(declaration instanceof CallableMemberDescriptor)) continue;
|
generateDelegationToTraitImpl(entry.getKey(), entry.getValue());
|
||||||
|
|
||||||
CallableMemberDescriptor inheritedMember = (CallableMemberDescriptor) declaration;
|
|
||||||
CallableMemberDescriptor traitMember = BridgesPackage.findTraitImplementation(inheritedMember);
|
|
||||||
if (traitMember == null) continue;
|
|
||||||
|
|
||||||
assert traitMember.getModality() != Modality.ABSTRACT : "Cannot delegate to abstract trait method: " + inheritedMember;
|
|
||||||
|
|
||||||
// inheritedMember can be abstract here. In order for FunctionCodegen to generate the method body, we're creating a copy here
|
|
||||||
// with traitMember's modality
|
|
||||||
CallableMemberDescriptor copy =
|
|
||||||
inheritedMember.copy(inheritedMember.getContainingDeclaration(), traitMember.getModality(), Visibilities.PUBLIC,
|
|
||||||
CallableMemberDescriptor.Kind.DECLARATION, true);
|
|
||||||
|
|
||||||
if (traitMember instanceof SimpleFunctionDescriptor) {
|
|
||||||
generateDelegationToTraitImpl((FunctionDescriptor) traitMember, (FunctionDescriptor) copy);
|
|
||||||
}
|
|
||||||
else if (traitMember instanceof PropertyDescriptor) {
|
|
||||||
for (PropertyAccessorDescriptor traitAccessor : ((PropertyDescriptor) traitMember).getAccessors()) {
|
|
||||||
for (PropertyAccessorDescriptor inheritedAccessor : ((PropertyDescriptor) copy).getAccessors()) {
|
|
||||||
if (inheritedAccessor.getClass() == traitAccessor.getClass()) { // same accessor kind
|
|
||||||
generateDelegationToTraitImpl(traitAccessor, inheritedAccessor);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user