Do not rely on JetCallExpressions in tail-call detection
Calls come in other forms too
This commit is contained in:
@@ -1595,9 +1595,10 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
|||||||
if (returnedExpression != null) {
|
if (returnedExpression != null) {
|
||||||
if (returnedExpression instanceof JetCallExpression) {
|
if (returnedExpression instanceof JetCallExpression) {
|
||||||
JetCallExpression callExpression = (JetCallExpression) returnedExpression;
|
JetCallExpression callExpression = (JetCallExpression) returnedExpression;
|
||||||
if (tailRecursionGeneratorUtil.isTailRecursion(callExpression) && callExpression.getCalleeExpression() != null) {
|
JetExpression calleeExpression = callExpression.getCalleeExpression();
|
||||||
ResolvedCall<? extends CallableDescriptor> resolvedCall = bindingContext.get(BindingContext.RESOLVED_CALL, callExpression.getCalleeExpression());
|
if (calleeExpression != null) {
|
||||||
if (resolvedCall != null) {
|
ResolvedCall<? extends CallableDescriptor> resolvedCall = bindingContext.get(BindingContext.RESOLVED_CALL, calleeExpression);
|
||||||
|
if (resolvedCall != null && tailRecursionGeneratorUtil.isTailRecursion(resolvedCall)) {
|
||||||
return tailRecursionGeneratorUtil.generateTailRecursion(resolvedCall, callExpression);
|
return tailRecursionGeneratorUtil.generateTailRecursion(resolvedCall, callExpression);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1932,7 +1933,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (tailRecursionGeneratorUtil.isTailRecursion(expression)) {
|
if (tailRecursionGeneratorUtil.isTailRecursion(resolvedCall)) {
|
||||||
return tailRecursionGeneratorUtil.generateTailRecursion(resolvedCall, expression);
|
return tailRecursionGeneratorUtil.generateTailRecursion(resolvedCall, expression);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -61,8 +61,8 @@ public class TailRecursionGeneratorUtil {
|
|||||||
this.state = state;
|
this.state = state;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isTailRecursion(@NotNull JetCallExpression expression) {
|
public boolean isTailRecursion(@NotNull ResolvedCall<?> resolvedCall) {
|
||||||
TailRecursionKind status = state.getBindingContext().get(TAIL_RECURSION_CALL, expression);
|
TailRecursionKind status = state.getBindingContext().get(TAIL_RECURSION_CALL, resolvedCall);
|
||||||
return status != null && status.isDoGenerateTailRecursion();
|
return status != null && status.isDoGenerateTailRecursion();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -336,8 +336,8 @@ public interface Errors {
|
|||||||
DiagnosticFactory2<JetReferenceExpression, JetExpression, JetType> FUNCTION_EXPECTED = DiagnosticFactory2.create(ERROR);
|
DiagnosticFactory2<JetReferenceExpression, JetExpression, JetType> FUNCTION_EXPECTED = DiagnosticFactory2.create(ERROR);
|
||||||
DiagnosticFactory2<JetExpression, JetExpression, Boolean> FUNCTION_CALL_EXPECTED = DiagnosticFactory2.create(ERROR, CALL_EXPRESSION);
|
DiagnosticFactory2<JetExpression, JetExpression, Boolean> FUNCTION_CALL_EXPECTED = DiagnosticFactory2.create(ERROR, CALL_EXPRESSION);
|
||||||
|
|
||||||
DiagnosticFactory0<JetCallExpression> NON_TAIL_RECURSIVE_CALL = DiagnosticFactory0.create(WARNING, CALL_EXPRESSION);
|
DiagnosticFactory0<PsiElement> NON_TAIL_RECURSIVE_CALL = DiagnosticFactory0.create(WARNING, CALL_EXPRESSION);
|
||||||
DiagnosticFactory0<JetCallExpression> TAIL_RECURSION_IN_TRY_IS_NOT_SUPPORTED = DiagnosticFactory0.create(WARNING, CALL_EXPRESSION);
|
DiagnosticFactory0<PsiElement> TAIL_RECURSION_IN_TRY_IS_NOT_SUPPORTED = DiagnosticFactory0.create(WARNING, CALL_EXPRESSION);
|
||||||
|
|
||||||
DiagnosticFactory0<PsiElement> NO_CONSTRUCTOR = DiagnosticFactory0.create(ERROR);
|
DiagnosticFactory0<PsiElement> NO_CONSTRUCTOR = DiagnosticFactory0.create(ERROR);
|
||||||
DiagnosticFactory0<PsiElement> CREATING_AN_INSTANCE_OF_ABSTRACT_CLASS = DiagnosticFactory0.create(ERROR);
|
DiagnosticFactory0<PsiElement> CREATING_AN_INSTANCE_OF_ABSTRACT_CLASS = DiagnosticFactory0.create(ERROR);
|
||||||
|
|||||||
@@ -383,10 +383,10 @@ public class PositioningStrategies {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
public static final PositioningStrategy<JetExpression> CALL_EXPRESSION = new PositioningStrategy<JetExpression>() {
|
public static final PositioningStrategy<PsiElement> CALL_EXPRESSION = new PositioningStrategy<PsiElement>() {
|
||||||
@NotNull
|
@NotNull
|
||||||
@Override
|
@Override
|
||||||
public List<TextRange> mark(@NotNull JetExpression element) {
|
public List<TextRange> mark(@NotNull PsiElement element) {
|
||||||
if (element instanceof JetCallExpression) {
|
if (element instanceof JetCallExpression) {
|
||||||
JetCallExpression callExpression = (JetCallExpression) element;
|
JetCallExpression callExpression = (JetCallExpression) element;
|
||||||
PsiElement endElement;
|
PsiElement endElement;
|
||||||
|
|||||||
@@ -89,7 +89,7 @@ public interface BindingContext {
|
|||||||
new BasicWritableSlice<JetReferenceExpression, DeclarationDescriptor>(DO_NOTHING);
|
new BasicWritableSlice<JetReferenceExpression, DeclarationDescriptor>(DO_NOTHING);
|
||||||
WritableSlice<JetElement, ResolvedCall<? extends CallableDescriptor>> RESOLVED_CALL =
|
WritableSlice<JetElement, ResolvedCall<? extends CallableDescriptor>> RESOLVED_CALL =
|
||||||
new BasicWritableSlice<JetElement, ResolvedCall<? extends CallableDescriptor>>(DO_NOTHING);
|
new BasicWritableSlice<JetElement, ResolvedCall<? extends CallableDescriptor>>(DO_NOTHING);
|
||||||
WritableSlice<JetCallExpression, TailRecursionKind> TAIL_RECURSION_CALL = new BasicWritableSlice<JetCallExpression, TailRecursionKind>(DO_NOTHING, true);
|
WritableSlice<ResolvedCall<?>, TailRecursionKind> TAIL_RECURSION_CALL = Slices.createSimpleSlice();
|
||||||
WritableSlice<FunctionDescriptor, Boolean> HAS_TAIL_CALLS = Slices.createSimpleSetSlice();
|
WritableSlice<FunctionDescriptor, Boolean> HAS_TAIL_CALLS = Slices.createSimpleSetSlice();
|
||||||
WritableSlice<JetElement, ConstraintSystemCompleter> CONSTRAINT_SYSTEM_COMPLETER = new BasicWritableSlice<JetElement, ConstraintSystemCompleter>(DO_NOTHING);
|
WritableSlice<JetElement, ConstraintSystemCompleter> CONSTRAINT_SYSTEM_COMPLETER = new BasicWritableSlice<JetElement, ConstraintSystemCompleter>(DO_NOTHING);
|
||||||
WritableSlice<JetElement, Call> CALL = new BasicWritableSlice<JetElement, Call>(DO_NOTHING);
|
WritableSlice<JetElement, Call> CALL = new BasicWritableSlice<JetElement, Call>(DO_NOTHING);
|
||||||
|
|||||||
Reference in New Issue
Block a user