From 8a14087c91635ba79327e46739ced97509b1794c Mon Sep 17 00:00:00 2001 From: Mikhael Bogdanov Date: Thu, 4 Apr 2013 10:37:37 +0400 Subject: [PATCH] Refactoring: property processing generalization --- .../jet/codegen/ExpressionCodegen.java | 121 ++++++++---------- .../codegen/ImplementationBodyCodegen.java | 4 +- .../org/jetbrains/jet/codegen/StackValue.java | 43 ++----- .../jet/lang/resolve/DescriptorUtils.java | 3 + 4 files changed, 68 insertions(+), 103 deletions(-) diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java index 50afdb3b619..7a35681db92 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java @@ -1535,18 +1535,18 @@ public class ExpressionCodegen extends JetVisitor implem // descriptor = ((VariableAsFunctionDescriptor) descriptor).getVariableDescriptor(); //} - IntrinsicMethod intrinsic = null; if (descriptor instanceof CallableMemberDescriptor) { CallableMemberDescriptor memberDescriptor = (CallableMemberDescriptor) descriptor; memberDescriptor = unwrapFakeOverride(memberDescriptor); - intrinsic = state.getIntrinsics().getIntrinsic(memberDescriptor); - } - if (intrinsic != null) { - Type expectedType = expressionType(expression); - return intrinsic.generate(this, v, expectedType, expression, Collections.emptyList(), receiver, state); + IntrinsicMethod intrinsic = state.getIntrinsics().getIntrinsic(memberDescriptor); + if (intrinsic != null) { + Type expectedType = expressionType(expression); + return intrinsic.generate(this, v, expectedType, expression, Collections.emptyList(), receiver, state); + } } + assert descriptor != null; DeclarationDescriptor container = descriptor.getContainingDeclaration(); @@ -1699,22 +1699,25 @@ public class ExpressionCodegen extends JetVisitor implem boolean forceField, @Nullable JetSuperExpression superExpression ) { - boolean isSuper = superExpression != null; DeclarationDescriptor containingDeclaration = propertyDescriptor.getContainingDeclaration(); assert containingDeclaration != null; containingDeclaration = containingDeclaration.getOriginal(); boolean isStatic = containingDeclaration instanceof NamespaceDescriptor; + boolean isSuper = superExpression != null; boolean overridesTrait = isOverrideForTrait(propertyDescriptor); boolean isFakeOverride = propertyDescriptor.getKind() == CallableMemberDescriptor.Kind.FAKE_OVERRIDE; + PropertyDescriptor initialDescriptor = propertyDescriptor; propertyDescriptor = initialDescriptor.getOriginal(); boolean isInsideClass = isCallInsideSameClassAsDeclared(propertyDescriptor, context); boolean isInsideModule = isCallInsideSameModuleAsDeclared(propertyDescriptor, context); boolean isExtensionProperty = propertyDescriptor.getReceiverParameter() != null; + Method getter = null; Method setter = null; + if (!forceField) { //noinspection ConstantConditions if (isInsideClass && @@ -1744,87 +1747,69 @@ public class ExpressionCodegen extends JetVisitor implem propertyDescriptor = accessablePropertyDescriptor(propertyDescriptor); } - getter = typeMapper.mapGetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION).getJvmMethodSignature().getAsmMethod(); - - if (propertyDescriptor.getGetter() == null) { - getter = null; + if (propertyDescriptor.getGetter() != null) { + getter = typeMapper. + mapGetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION). + getJvmMethodSignature().getAsmMethod(); } - if (getter == null && propertyDescriptor.getReceiverParameter() != null) { + if (getter == null && isExtensionProperty) { throw new IllegalStateException(); } } - //noinspection ConstantConditions - if (!propertyDescriptor.isVar() || isInsideClass && !isExtensionProperty && - (propertyDescriptor.getSetter() == null || - !DescriptorUtils.isExternallyAccessible(propertyDescriptor) || - propertyDescriptor.getSetter().isDefault() && - propertyDescriptor.getSetter().getModality() == Modality.FINAL)) { - setter = null; - } - else { - JvmPropertyAccessorSignature jvmMethodSignature = - typeMapper.mapSetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION); - setter = jvmMethodSignature != null ? jvmMethodSignature.getJvmMethodSignature().getAsmMethod() : null; - if (propertyDescriptor.getSetter() == null) { - setter = null; + if (propertyDescriptor.isVar()) { + if (propertyDescriptor.getSetter() != null) { + if (isInsideClass && !isExtensionProperty && + (!DescriptorUtils.isExternallyAccessible(propertyDescriptor) || + propertyDescriptor.getSetter().isDefault() && + propertyDescriptor.getSetter().getModality() == Modality.FINAL)) { + setter = null; + } + else { + setter = typeMapper. + mapSetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION). + getJvmMethodSignature().getAsmMethod(); + } } - if (setter == null && propertyDescriptor.isVar() && propertyDescriptor.getReceiverParameter() != null) { + if (setter == null && isExtensionProperty) { throw new IllegalStateException(); } } } - int getterInvokeOpcode; - int setterInvokeOpcode; + int getterInvokeOpcode = getOpcodeForPropertyDescriptorWithoutAccessor(propertyDescriptor); + int setterInvokeOpcode = getterInvokeOpcode; + + CallableMethod callableGetter = null; + CallableMethod callableSetter = null; + + if (getter != null) { + callableGetter = typeMapper.mapToCallableMethod(propertyDescriptor.getGetter(), isSuper, isInsideClass, isInsideModule, contextKind()); + getterInvokeOpcode = callableGetter.getInvokeOpcode(); + } + + if (setter != null) { + callableSetter = typeMapper.mapToCallableMethod(propertyDescriptor.getSetter(), isSuper, isInsideClass, isInsideModule, contextKind()); + setterInvokeOpcode = callableSetter.getInvokeOpcode(); + } JvmClassName owner; - JvmClassName ownerParam; - boolean isInterface; - if (isStatic) { - isInterface = overridesTrait; - owner = ownerParam = typeMapper.getOwner(propertyDescriptor, contextKind(), isInsideModule); + CallableMethod callableMethod = callableGetter != null ? callableGetter : callableSetter; - getterInvokeOpcode = INVOKESTATIC; - setterInvokeOpcode = INVOKESTATIC; + if (callableMethod == null) { + owner = typeMapper.getOwner(propertyDescriptor, contextKind(), isInsideModule); } else { - isInterface = isInterface(containingDeclaration) || overridesTrait; - CallableMethod callableGetter = null; - CallableMethod callableSetter = null; - if (getter == null) { - getterInvokeOpcode = getOpcodeForPropertyDescriptorWithoutAccessor(propertyDescriptor); - } - else { - callableGetter = typeMapper.mapToCallableMethod(propertyDescriptor.getGetter(), isSuper, isInsideClass, isInsideModule, contextKind()); - getterInvokeOpcode = callableGetter.getInvokeOpcode(); - } - - if (setter == null) { - setterInvokeOpcode = getOpcodeForPropertyDescriptorWithoutAccessor(propertyDescriptor); - } - else { - callableSetter = typeMapper.mapToCallableMethod(propertyDescriptor.getSetter(), isSuper, isInsideClass, isInsideModule, contextKind()); - setterInvokeOpcode = callableSetter.getInvokeOpcode(); - } - - CallableMethod callableMethod = callableGetter != null ? callableGetter : callableSetter; - if (callableMethod == null) { - owner = ownerParam = typeMapper.getOwner(propertyDescriptor, contextKind(), isInsideModule); - } - else { - owner = isFakeOverride && !overridesTrait && !isInterface(initialDescriptor.getContainingDeclaration()) - ? JvmClassName.byType(typeMapper.mapType( - ((ClassDescriptor) initialDescriptor.getContainingDeclaration()).getDefaultType(), JetTypeMapperMode.IMPL)) - : callableMethod.getOwner(); - ownerParam = callableMethod.getDefaultImplParam(); - } + owner = isFakeOverride && !overridesTrait && !isInterface(initialDescriptor.getContainingDeclaration()) + ? JvmClassName.byType(typeMapper.mapType( + ((ClassDescriptor) initialDescriptor.getContainingDeclaration()).getDefaultType(), JetTypeMapperMode.IMPL)) + : callableMethod.getOwner(); } - return StackValue.property(propertyDescriptor, owner, ownerParam, asmType(propertyDescriptor.getType()), - isStatic, isInterface, isSuper, getter, setter, getterInvokeOpcode, setterInvokeOpcode, state); + return StackValue.property(propertyDescriptor, owner, asmType(propertyDescriptor.getType()), + isStatic, getter, setter, getterInvokeOpcode, setterInvokeOpcode, state); } private static int getOpcodeForPropertyDescriptorWithoutAccessor(PropertyDescriptor descriptor) { diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java index a0f22584982..da3edd2d377 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java @@ -1620,8 +1620,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen { // @todo write directly to the field. Fix test excloset.jet::test6 JvmClassName owner = typeMapper.getOwner(propertyDescriptor, OwnerKind.IMPLEMENTATION, isCallInsideSameModuleAsDeclared(propertyDescriptor, codegen.context)); Type propType = typeMapper.mapType(jetType); - StackValue.property(propertyDescriptor, owner, owner, - propType, false, false, false, null, null, 0, 0, state).store(propType, iv); + StackValue.property(propertyDescriptor, owner, + propType, false, null, null, 0, 0, state).store(propType, iv); } } } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java b/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java index 102d00772d5..8fe805a9403 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java @@ -137,18 +137,15 @@ public abstract class StackValue { public static Property property( PropertyDescriptor descriptor, JvmClassName methodOwner, - JvmClassName methodOwnerParam, Type type, boolean isStatic, - boolean isInterface, - boolean isSuper, @Nullable Method getter, @Nullable Method setter, int getterInvokeOpcode, int setterInvokeOpcode, GenerationState state ) { - return new Property(descriptor, methodOwner, methodOwnerParam, getter, setter, isStatic, isInterface, isSuper, type, getterInvokeOpcode, setterInvokeOpcode, + return new Property(descriptor, methodOwner, getter, setter, isStatic, type, getterInvokeOpcode, setterInvokeOpcode, state); } @@ -866,11 +863,7 @@ public abstract class StackValue { private final Method setter; @NotNull public final JvmClassName methodOwner; - @NotNull - private final JvmClassName methodOwnerParam; - private final boolean isInterface; - private final boolean isSuper; private final int getterInvokeOpcode; private final int setterInvokeOpcode; @NotNull @@ -879,17 +872,14 @@ public abstract class StackValue { private final GenerationState state; public Property( - @NotNull PropertyDescriptor descriptor, @NotNull JvmClassName methodOwner, @NotNull JvmClassName methodOwnerParam, - @Nullable Method getter, @Nullable Method setter, boolean isStatic, boolean isInterface, boolean isSuper, + @NotNull PropertyDescriptor descriptor, @NotNull JvmClassName methodOwner, + @Nullable Method getter, @Nullable Method setter, boolean isStatic, @NotNull Type type, int getterInvokeOpcode, int setterInvokeOpcode, @NotNull GenerationState state ) { super(type, isStatic); this.methodOwner = methodOwner; - this.methodOwnerParam = methodOwnerParam; this.getter = getter; this.setter = setter; - this.isInterface = isInterface; - this.isSuper = isSuper; this.getterInvokeOpcode = getterInvokeOpcode; this.setterInvokeOpcode = setterInvokeOpcode; this.descriptor = descriptor; @@ -904,20 +894,13 @@ public abstract class StackValue { @Override public void put(Type type, InstructionAdapter v) { - if (isSuper && isInterface) { - assert getter != null; - v.visitMethodInsn(INVOKESTATIC, methodOwner.getInternalName(), getter.getName(), - getter.getDescriptor().replace("(", "(" + methodOwnerParam.getDescriptor())); + if (getter == null) { + v.visitFieldInsn(isStatic ? GETSTATIC : GETFIELD, methodOwner.getInternalName(), descriptor.getName().getName(), + this.type.getDescriptor()); + genNotNullAssertionForField(v, state, descriptor); } else { - if (getter == null) { - v.visitFieldInsn(isStatic ? GETSTATIC : GETFIELD, methodOwner.getInternalName(), descriptor.getName().getName(), - this.type.getDescriptor()); - genNotNullAssertionForField(v, state, descriptor); - } - else { - v.visitMethodInsn(getterInvokeOpcode, methodOwner.getInternalName(), getter.getName(), getter.getDescriptor()); - } + v.visitMethodInsn(getterInvokeOpcode, methodOwner.getInternalName(), getter.getName(), getter.getDescriptor()); } coerceTo(type, v); } @@ -925,15 +908,9 @@ public abstract class StackValue { @Override public void store(Type topOfStackType, InstructionAdapter v) { coerceFrom(topOfStackType, v); - if (isSuper && isInterface) { - assert setter != null; - v.visitMethodInsn(INVOKESTATIC, methodOwner.getInternalName(), setter.getName(), - setter.getDescriptor().replace("(", "(" + methodOwnerParam.getDescriptor())); - } - else if (setter == null) { + if (setter == null) { v.visitFieldInsn(isStatic ? PUTSTATIC : PUTFIELD, methodOwner.getInternalName(), descriptor.getName().getName(), - this.type.getDescriptor()); - } + this.type.getDescriptor()); } else { v.visitMethodInsn(setterInvokeOpcode, methodOwner.getInternalName(), setter.getName(), setter.getDescriptor()); } diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/DescriptorUtils.java b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/DescriptorUtils.java index d50e8702e03..a11e891545d 100644 --- a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/DescriptorUtils.java +++ b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/DescriptorUtils.java @@ -159,6 +159,9 @@ public class DescriptorUtils { @Nullable public static DeclarationDescriptor findTopLevelParent(@NotNull DeclarationDescriptor declarationDescriptor) { DeclarationDescriptor descriptor = declarationDescriptor; + if (declarationDescriptor instanceof PropertyAccessorDescriptor) { + descriptor = ((PropertyAccessorDescriptor)descriptor).getCorrespondingProperty(); + } while (!(descriptor == null || isTopLevelDeclaration(descriptor))) { descriptor = descriptor.getContainingDeclaration(); }