Access private class property via field in Evaluate Expression
This commit is contained in:
@@ -1836,7 +1836,6 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
|||||||
boolean isBackingFieldInAnotherClass = AsmUtil.isPropertyWithBackingFieldInOuterClass(propertyDescriptor);
|
boolean isBackingFieldInAnotherClass = AsmUtil.isPropertyWithBackingFieldInOuterClass(propertyDescriptor);
|
||||||
boolean isStatic = containingDeclaration instanceof PackageFragmentDescriptor;
|
boolean isStatic = containingDeclaration instanceof PackageFragmentDescriptor;
|
||||||
boolean isSuper = superExpression != null;
|
boolean isSuper = superExpression != null;
|
||||||
boolean isInsideClass = isCallInsideSameClassAsDeclared(propertyDescriptor, context);
|
|
||||||
boolean isExtensionProperty = propertyDescriptor.getReceiverParameter() != null;
|
boolean isExtensionProperty = propertyDescriptor.getReceiverParameter() != null;
|
||||||
|
|
||||||
JetType delegateType = getPropertyDelegateType(propertyDescriptor, bindingContext);
|
JetType delegateType = getPropertyDelegateType(propertyDescriptor, bindingContext);
|
||||||
@@ -1861,7 +1860,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!skipPropertyAccessors) {
|
if (!skipPropertyAccessors) {
|
||||||
if (couldUseDirectAccessToProperty(propertyDescriptor, true, isInsideClass, isDelegatedProperty, context)) {
|
if (couldUseDirectAccessToProperty(propertyDescriptor, true, isDelegatedProperty, context)) {
|
||||||
callableGetter = null;
|
callableGetter = null;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@@ -1885,7 +1884,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
|||||||
if (propertyDescriptor.isVar()) {
|
if (propertyDescriptor.isVar()) {
|
||||||
PropertySetterDescriptor setter = propertyDescriptor.getSetter();
|
PropertySetterDescriptor setter = propertyDescriptor.getSetter();
|
||||||
if (setter != null) {
|
if (setter != null) {
|
||||||
if (couldUseDirectAccessToProperty(propertyDescriptor, false, isInsideClass, isDelegatedProperty, context)) {
|
if (couldUseDirectAccessToProperty(propertyDescriptor, false, isDelegatedProperty, context)) {
|
||||||
callableSetter = null;
|
callableSetter = null;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
|||||||
@@ -34,6 +34,9 @@ import org.jetbrains.jet.lang.descriptors.*;
|
|||||||
import org.jetbrains.jet.lang.descriptors.annotations.Annotations;
|
import org.jetbrains.jet.lang.descriptors.annotations.Annotations;
|
||||||
import org.jetbrains.jet.lang.descriptors.impl.SimpleFunctionDescriptorImpl;
|
import org.jetbrains.jet.lang.descriptors.impl.SimpleFunctionDescriptorImpl;
|
||||||
import org.jetbrains.jet.lang.descriptors.impl.TypeParameterDescriptorImpl;
|
import org.jetbrains.jet.lang.descriptors.impl.TypeParameterDescriptorImpl;
|
||||||
|
import org.jetbrains.jet.lang.psi.JetFile;
|
||||||
|
import org.jetbrains.jet.lang.psi.codeFragmentUtil.CodeFragmentUtilPackage;
|
||||||
|
import org.jetbrains.jet.lang.resolve.DescriptorToSourceUtils;
|
||||||
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
||||||
import org.jetbrains.jet.lang.resolve.calls.CallResolverUtil;
|
import org.jetbrains.jet.lang.resolve.calls.CallResolverUtil;
|
||||||
import org.jetbrains.jet.lang.resolve.java.descriptor.JavaPackageFragmentDescriptor;
|
import org.jetbrains.jet.lang.resolve.java.descriptor.JavaPackageFragmentDescriptor;
|
||||||
@@ -151,12 +154,11 @@ public class JvmCodegenUtil {
|
|||||||
return type.getConstructor().getDeclarationDescriptor().getOriginal() == classifier.getOriginal();
|
return type.getConstructor().getDeclarationDescriptor().getOriginal() == classifier.getOriginal();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean isCallInsideSameClassAsDeclared(CallableMemberDescriptor declarationDescriptor, CodegenContext context) {
|
private static boolean isCallInsideSameClassAsDeclared(@NotNull CallableMemberDescriptor descriptor, @NotNull CodegenContext context) {
|
||||||
boolean isFakeOverride = declarationDescriptor.getKind() == CallableMemberDescriptor.Kind.FAKE_OVERRIDE;
|
boolean isFakeOverride = descriptor.getKind() == CallableMemberDescriptor.Kind.FAKE_OVERRIDE;
|
||||||
boolean isDelegate = declarationDescriptor.getKind() == CallableMemberDescriptor.Kind.DELEGATION;
|
boolean isDelegate = descriptor.getKind() == CallableMemberDescriptor.Kind.DELEGATION;
|
||||||
|
|
||||||
DeclarationDescriptor containingDeclaration = declarationDescriptor.getContainingDeclaration();
|
DeclarationDescriptor containingDeclaration = descriptor.getContainingDeclaration().getOriginal();
|
||||||
containingDeclaration = containingDeclaration.getOriginal();
|
|
||||||
|
|
||||||
return !isFakeOverride && !isDelegate &&
|
return !isFakeOverride && !isDelegate &&
|
||||||
(((context.hasThisDescriptor() && containingDeclaration == context.getThisDescriptor()) ||
|
(((context.hasThisDescriptor() && containingDeclaration == context.getThisDescriptor()) ||
|
||||||
@@ -249,7 +251,6 @@ public class JvmCodegenUtil {
|
|||||||
public static boolean couldUseDirectAccessToProperty(
|
public static boolean couldUseDirectAccessToProperty(
|
||||||
@NotNull PropertyDescriptor property,
|
@NotNull PropertyDescriptor property,
|
||||||
boolean forGetter,
|
boolean forGetter,
|
||||||
boolean isInsideClass,
|
|
||||||
boolean isDelegated,
|
boolean isDelegated,
|
||||||
@NotNull MethodContext context
|
@NotNull MethodContext context
|
||||||
) {
|
) {
|
||||||
@@ -258,8 +259,8 @@ public class JvmCodegenUtil {
|
|||||||
// Inline functions can't use direct access because a field may not be visible at the call site
|
// Inline functions can't use direct access because a field may not be visible at the call site
|
||||||
if (context.isInlineFunction()) return false;
|
if (context.isInlineFunction()) return false;
|
||||||
|
|
||||||
// Only properties of the same class can be directly accessed
|
// Only properties of the same class can be directly accessed, except when we are evaluating expressions in the debugger
|
||||||
if (!isInsideClass) return false;
|
if (!isCallInsideSameClassAsDeclared(property, context) && !isDebuggerContext(context)) return false;
|
||||||
|
|
||||||
// Delegated and extension properties have no backing fields
|
// Delegated and extension properties have no backing fields
|
||||||
if (isDelegated || property.getReceiverParameter() != null) return false;
|
if (isDelegated || property.getReceiverParameter() != null) return false;
|
||||||
@@ -279,6 +280,11 @@ public class JvmCodegenUtil {
|
|||||||
return property.getVisibility() == Visibilities.PRIVATE || accessor.getModality() == FINAL;
|
return property.getVisibility() == Visibilities.PRIVATE || accessor.getModality() == FINAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static boolean isDebuggerContext(@NotNull MethodContext context) {
|
||||||
|
JetFile file = DescriptorToSourceUtils.getContainingFile(context.getContextDescriptor());
|
||||||
|
return file != null && CodeFragmentUtilPackage.getSkipVisibilityCheck(file);
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static ImplementationBodyCodegen getParentBodyCodegen(@Nullable MemberCodegen<?> classBodyCodegen) {
|
public static ImplementationBodyCodegen getParentBodyCodegen(@Nullable MemberCodegen<?> classBodyCodegen) {
|
||||||
assert classBodyCodegen != null && classBodyCodegen.getParentCodegen() instanceof ImplementationBodyCodegen
|
assert classBodyCodegen != null && classBodyCodegen.getParentCodegen() instanceof ImplementationBodyCodegen
|
||||||
|
|||||||
Reference in New Issue
Block a user