diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java index 9e5102c5530..3bd8a95e150 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java @@ -1339,7 +1339,7 @@ public class ExpressionCodegen extends JetVisitor { } private StackValue invokeFunction(JetCallExpression expression, - DeclarationDescriptor fd, + FunctionDescriptor fd, StackValue receiver, ResolvedCall resolvedCall) { boolean superCall = false; @@ -1357,7 +1357,7 @@ public class ExpressionCodegen extends JetVisitor { while(c.getContextDescriptor() != enclosed) { c = c.getParentContext(); } - fd = c.getAccessor(fd); + fd = (FunctionDescriptor) c.getAccessor(fd); superCall = false; receiver = StackValue.thisOrOuter(this, enclosed); } @@ -1365,13 +1365,27 @@ public class ExpressionCodegen extends JetVisitor { } } - Callable callable = resolveToCallable((FunctionDescriptor) fd, superCall); + if (fd.getVisibility() == Visibilities.PRIVATE + && !DescriptorUtils.isClassObject(fd.getContainingDeclaration())) { + if (context.getClassOrNamespaceDescriptor() != fd.getContainingDeclaration()) { + DeclarationDescriptor enclosed = fd.getContainingDeclaration(); + if (enclosed != context.getThisDescriptor()) { + CodegenContext c = context; + while(c.getContextDescriptor() != enclosed) { + c = c.getParentContext(); + } + fd = (FunctionDescriptor) c.getAccessor(fd); + } + } + } + + Callable callable = resolveToCallable(fd, superCall); if (callable instanceof CallableMethod) { final CallableMethod callableMethod = (CallableMethod) callable; invokeMethodWithArguments(callableMethod, expression, receiver); final Type callReturnType = callableMethod.getSignature().getAsmMethod().getReturnType(); - return returnValueAsStackValue((FunctionDescriptor) fd, callReturnType); + return returnValueAsStackValue(fd, callReturnType); } else { receiver = StackValue.receiver(resolvedCall, receiver, this, null, state); diff --git a/compiler/testData/codegen/classes/privateOuterFunctions.kt b/compiler/testData/codegen/classes/privateOuterFunctions.kt new file mode 100644 index 00000000000..0487bd4cb7e --- /dev/null +++ b/compiler/testData/codegen/classes/privateOuterFunctions.kt @@ -0,0 +1,31 @@ +class C { + private fun String.ext() : String = "" + private fun f() {} + + public fun foo() : String { + { + "".ext() + f() + }.invoke() + + object : Runnable { + public override fun run() { + "".ext() + f() + } + }.run() + + Inner().innerFun() + + return "OK" + } + + private class Inner() { + fun innerFun() { + "".ext() + f() + } + } +} + +fun box() = C().foo() \ No newline at end of file diff --git a/compiler/testData/codegen/classes/privateOuterProperty.kt b/compiler/testData/codegen/classes/privateOuterProperty.kt new file mode 100644 index 00000000000..70afd19a592 --- /dev/null +++ b/compiler/testData/codegen/classes/privateOuterProperty.kt @@ -0,0 +1,27 @@ +class C{ + private var v : Int = 0 + + public fun foo() : Int { + { + v = v + 1 + }.invoke() + + object : Runnable { + public override fun run() { + v = v + 1 + } + }.run() + + Inner().innerFun() + + return v + } + + private class Inner() { + fun innerFun() { + v = v + 1 + } + } +} + +fun box() = if (C().foo() == 3) "OK" else "NOT OK" \ No newline at end of file diff --git a/compiler/tests/org/jetbrains/jet/codegen/ClassGenTest.java b/compiler/tests/org/jetbrains/jet/codegen/ClassGenTest.java index 01fa0fefcd6..d00dc4b1441 100644 --- a/compiler/tests/org/jetbrains/jet/codegen/ClassGenTest.java +++ b/compiler/tests/org/jetbrains/jet/codegen/ClassGenTest.java @@ -231,6 +231,16 @@ public class ClassGenTest extends CodegenTestCase { blackBox(); } + public void testPrivateOuterProperty() throws Exception { + createEnvironmentWithMockJdkAndIdeaAnnotations(CompilerSpecialMode.JDK_HEADERS); + blackBoxFile("classes/privateOuterProperty.kt"); + } + + public void testPrivateOuterFunctions() throws Exception { + createEnvironmentWithMockJdkAndIdeaAnnotations(CompilerSpecialMode.JDK_HEADERS); + blackBoxFile("classes/privateOuterFunctions.kt"); + } + public void testKt249() throws Exception { createEnvironmentWithMockJdkAndIdeaAnnotations(CompilerSpecialMode.JDK_HEADERS); blackBoxFile("regressions/kt249.jet");