Debugger: Fix VariableAsFunctionResolvedCall evaluation

This commit is contained in:
Yan Zhulanow
2019-04-23 06:33:34 +09:00
parent 4a90e9d0ab
commit 999d5ce3bb
4 changed files with 51 additions and 11 deletions
@@ -75,6 +75,12 @@ class CodeFragmentParameterAnalyzer(
}
private fun processResolvedCall(resolvedCall: ResolvedCall<*>, expression: KtSimpleNameExpression) {
if (resolvedCall is VariableAsFunctionResolvedCall) {
processResolvedCall(resolvedCall.functionCall, expression)
processResolvedCall(resolvedCall.variableCall, expression)
return
}
// Capture dispatch receiver for the extension callable
run {
val descriptor = resolvedCall.resultingDescriptor
@@ -84,7 +90,8 @@ class CodeFragmentParameterAnalyzer(
&& extensionParameter != null && containingClass != null
) {
if (containingClass.kind != ClassKind.OBJECT) {
processDispatchReceiver(containingClass)
val parameter = processDispatchReceiver(containingClass)
checkBounds(descriptor, expression, parameter)
}
}
}
@@ -130,21 +137,16 @@ class CodeFragmentParameterAnalyzer(
// If a reference has receivers, we can calculate its value using them, no need to capture
if (!processed) {
if (resolvedCall is VariableAsFunctionResolvedCall) {
processResolvedCall(resolvedCall.functionCall, expression)
processResolvedCall(resolvedCall.variableCall, expression)
} else {
processDescriptor(resolvedCall.resultingDescriptor, expression)
}
val descriptor = resolvedCall.resultingDescriptor
val parameter = processDescriptor(descriptor, expression)
checkBounds(descriptor, expression, parameter)
}
}
private fun processDescriptor(descriptor: DeclarationDescriptor, expression: KtSimpleNameExpression) {
val parameter = processDebugLabel(descriptor)
private fun processDescriptor(descriptor: DeclarationDescriptor, expression: KtSimpleNameExpression): Smart? {
return processDebugLabel(descriptor)
?: processCoroutineContextCall(descriptor)
?: processSimpleNameExpression(descriptor, expression)
checkBounds(descriptor, expression, parameter)
}
override fun visitThisExpression(expression: KtThisExpression, data: Unit?): Void? {
@@ -0,0 +1,25 @@
package variableAsFunction
fun main() {
class Foo
class Bar {
operator fun Foo.invoke(f: Int) = f
}
with (Bar()) {
block {
val foo = Foo()
//Breakpoint!
val y = foo(5)
}
}
}
fun block(block: () -> Unit) {
block()
}
// EXPRESSION: foo(5)
// RESULT: 5: I
@@ -0,0 +1,8 @@
LineBreakpoint created at variableAsFunction.kt:14
Run Java
Connected to the target VM
variableAsFunction.kt:14
Compile bytecode for foo(5)
Disconnected from the target VM
Process finished with exit code 0
@@ -441,6 +441,11 @@ public class KotlinEvaluateExpressionTestGenerated extends AbstractKotlinEvaluat
runTest("idea/testData/debugger/tinyApp/src/evaluate/singleBreakpoint/valueParameterName.kt");
}
@TestMetadata("variableAsFunction.kt")
public void testVariableAsFunction() throws Exception {
runTest("idea/testData/debugger/tinyApp/src/evaluate/singleBreakpoint/variableAsFunction.kt");
}
@TestMetadata("vars.kt")
public void testVars() throws Exception {
runTest("idea/testData/debugger/tinyApp/src/evaluate/singleBreakpoint/vars.kt");