cache resolution data by callKey instead of expression

This commit is contained in:
Svetlana Isakova
2013-03-14 18:26:53 +04:00
parent 0bc647044c
commit cbbac2f2ef
3 changed files with 40 additions and 28 deletions
@@ -265,15 +265,14 @@ public class CallResolver {
@NotNull CallTransformer<D, F> callTransformer, @NotNull CallTransformer<D, F> callTransformer,
@NotNull JetReferenceExpression reference @NotNull JetReferenceExpression reference
) { ) {
PsiElement element = context.call.getCallElement();
OverloadResolutionResultsImpl<F> results = null; OverloadResolutionResultsImpl<F> results = null;
TracingStrategy tracing = prioritizedTasks.isEmpty() ? TracingStrategy.EMPTY : prioritizedTasks.iterator().next().tracing; TracingStrategy tracing = prioritizedTasks.isEmpty() ? TracingStrategy.EMPTY : prioritizedTasks.iterator().next().tracing;
TemporaryBindingTrace traceToResolveCall = TemporaryBindingTrace.create(context.trace, "trace to resolve call", context.call); TemporaryBindingTrace traceToResolveCall = TemporaryBindingTrace.create(context.trace, "trace to resolve call", context.call);
if (element instanceof JetExpression) { CallKey callKey = CallResolverUtil.createCallKey(context);
CallKey key = CallKey.create(context.call.getCallType(), (JetExpression) element); if (callKey != null) {
OverloadResolutionResultsImpl<F> cachedResults = context.resolutionResultsCache.getResolutionResults(key, memberType); OverloadResolutionResultsImpl<F> cachedResults = context.resolutionResultsCache.getResolutionResults(callKey, memberType);
if (cachedResults != null) { if (cachedResults != null) {
DelegatingBindingTrace deltasTraceForResolve = context.resolutionResultsCache.getResolutionTrace((JetExpression) element); DelegatingBindingTrace deltasTraceForResolve = context.resolutionResultsCache.getResolutionTrace(callKey);
assert deltasTraceForResolve != null; assert deltasTraceForResolve != null;
deltasTraceForResolve.addAllMyDataTo(traceToResolveCall); deltasTraceForResolve.addAllMyDataTo(traceToResolveCall);
results = cachedResults; results = cachedResults;
@@ -356,21 +355,20 @@ public class CallResolver {
@NotNull DelegatingBindingTrace traceToResolveCall, @NotNull DelegatingBindingTrace traceToResolveCall,
@NotNull TracingStrategy tracing @NotNull TracingStrategy tracing
) { ) {
PsiElement callElement = context.call.getCallElement();
if (!(callElement instanceof JetExpression)) return;
DelegatingBindingTrace deltasTraceToCacheResolve = new DelegatingBindingTrace( DelegatingBindingTrace deltasTraceToCacheResolve = new DelegatingBindingTrace(
new BindingTraceContext().getBindingContext(), "delta trace for caching resolve of", context.call); new BindingTraceContext().getBindingContext(), "delta trace for caching resolve of", context.call);
traceToResolveCall.addAllMyDataTo(deltasTraceToCacheResolve); traceToResolveCall.addAllMyDataTo(deltasTraceToCacheResolve);
JetExpression callExpression = (JetExpression) callElement; CallKey callKey = CallResolverUtil.createCallKey(context);
context.resolutionResultsCache.recordResolutionResults(CallKey.create(context.call.getCallType(), callExpression), memberType, results); if (callKey == null) return;
context.resolutionResultsCache.recordResolutionTrace(callExpression, deltasTraceToCacheResolve);
context.resolutionResultsCache.recordResolutionResults(callKey, memberType, results);
context.resolutionResultsCache.recordResolutionTrace(callKey, deltasTraceToCacheResolve);
if (results.isSingleResult() && memberType == ResolutionResultsCache.FUNCTION_MEMBER_TYPE) { if (results.isSingleResult() && memberType == ResolutionResultsCache.FUNCTION_MEMBER_TYPE) {
CallCandidateResolutionContext<F> callCandidateResolutionContext = CallCandidateResolutionContext.createForCallBeingAnalyzed( CallCandidateResolutionContext<F> callCandidateResolutionContext = CallCandidateResolutionContext.createForCallBeingAnalyzed(
results.getResultingCall().getCallToCompleteTypeArgumentInference(), context, tracing); results.getResultingCall().getCallToCompleteTypeArgumentInference(), context, tracing);
context.resolutionResultsCache.recordDeferredComputationForCall(callExpression, callCandidateResolutionContext, memberType); context.resolutionResultsCache.recordDeferredComputationForCall(callKey, callCandidateResolutionContext, memberType);
} }
} }
@@ -17,12 +17,18 @@
package org.jetbrains.jet.lang.resolve.calls; package org.jetbrains.jet.lang.resolve.calls;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import com.intellij.psi.PsiElement;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.lang.descriptors.CallableDescriptor; import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
import org.jetbrains.jet.lang.descriptors.TypeParameterDescriptor; import org.jetbrains.jet.lang.descriptors.TypeParameterDescriptor;
import org.jetbrains.jet.lang.descriptors.ValueParameterDescriptor; import org.jetbrains.jet.lang.descriptors.ValueParameterDescriptor;
import org.jetbrains.jet.lang.psi.Call;
import org.jetbrains.jet.lang.psi.CallKey;
import org.jetbrains.jet.lang.psi.JetExpression;
import org.jetbrains.jet.lang.resolve.BindingContext; import org.jetbrains.jet.lang.resolve.BindingContext;
import org.jetbrains.jet.lang.resolve.TraceUtil; import org.jetbrains.jet.lang.resolve.TraceUtil;
import org.jetbrains.jet.lang.resolve.calls.context.BasicCallResolutionContext;
import org.jetbrains.jet.lang.resolve.calls.context.CallResolutionContext; import org.jetbrains.jet.lang.resolve.calls.context.CallResolutionContext;
import org.jetbrains.jet.lang.resolve.calls.inference.ConstraintSystem; import org.jetbrains.jet.lang.resolve.calls.inference.ConstraintSystem;
import org.jetbrains.jet.lang.resolve.calls.inference.ConstraintsUtil; import org.jetbrains.jet.lang.resolve.calls.inference.ConstraintsUtil;
@@ -36,6 +42,8 @@ import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import static org.jetbrains.jet.lang.resolve.calls.CallTransformer.CallForImplicitInvoke;
public class CallResolverUtil { public class CallResolverUtil {
public static final JetType DONT_CARE = ErrorUtils.createErrorTypeWithCustomDebugName("DONT_CARE"); public static final JetType DONT_CARE = ErrorUtils.createErrorTypeWithCustomDebugName("DONT_CARE");
@@ -125,4 +133,14 @@ public class CallResolverUtil {
} }
return false; return false;
} }
@Nullable
public static CallKey createCallKey(@NotNull BasicCallResolutionContext context) {
if (context.call.getCallType() == Call.CallType.INVOKE) {
return null;
}
PsiElement callElement = context.call.getCallElement();
if (!(callElement instanceof JetExpression)) return null;
return CallKey.create(context.call.getCallType(), (JetExpression) callElement);
}
} }
@@ -22,11 +22,9 @@ import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor; import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
import org.jetbrains.jet.lang.descriptors.VariableDescriptor; import org.jetbrains.jet.lang.descriptors.VariableDescriptor;
import org.jetbrains.jet.lang.psi.CallKey; import org.jetbrains.jet.lang.psi.CallKey;
import org.jetbrains.jet.lang.psi.JetExpression;
import org.jetbrains.jet.lang.resolve.BindingTrace; import org.jetbrains.jet.lang.resolve.BindingTrace;
import org.jetbrains.jet.lang.resolve.BindingTraceContext; import org.jetbrains.jet.lang.resolve.BindingTraceContext;
import org.jetbrains.jet.lang.resolve.DelegatingBindingTrace; import org.jetbrains.jet.lang.resolve.DelegatingBindingTrace;
import org.jetbrains.jet.lang.resolve.calls.results.OverloadResolutionResults;
import org.jetbrains.jet.lang.resolve.calls.results.OverloadResolutionResultsImpl; import org.jetbrains.jet.lang.resolve.calls.results.OverloadResolutionResultsImpl;
import org.jetbrains.jet.util.slicedmap.Slices; import org.jetbrains.jet.util.slicedmap.Slices;
import org.jetbrains.jet.util.slicedmap.WritableSlice; import org.jetbrains.jet.util.slicedmap.WritableSlice;
@@ -34,16 +32,14 @@ import org.jetbrains.jet.util.slicedmap.WritableSlice;
public class ResolutionResultsCache { public class ResolutionResultsCache {
public static class MemberType<D extends CallableDescriptor> {} public static class MemberType<D extends CallableDescriptor> {}
private static class FunctionMemberType extends MemberType<FunctionDescriptor> {} public static final MemberType<FunctionDescriptor> FUNCTION_MEMBER_TYPE = new MemberType<FunctionDescriptor>();
private static class PropertyMemberType extends MemberType<VariableDescriptor> {} public static final MemberType<VariableDescriptor> PROPERTY_MEMBER_TYPE = new MemberType<VariableDescriptor>();
public static final FunctionMemberType FUNCTION_MEMBER_TYPE = new FunctionMemberType();
public static final PropertyMemberType PROPERTY_MEMBER_TYPE = new PropertyMemberType();
private static final WritableSlice<CallKey, OverloadResolutionResultsImpl<FunctionDescriptor>> RESOLUTION_RESULTS_FOR_FUNCTION = Slices.createSimpleSlice(); private static final WritableSlice<CallKey, OverloadResolutionResultsImpl<FunctionDescriptor>> RESOLUTION_RESULTS_FOR_FUNCTION = Slices.createSimpleSlice();
private static final WritableSlice<CallKey, OverloadResolutionResultsImpl<VariableDescriptor>> RESOLUTION_RESULTS_FOR_PROPERTY = Slices.createSimpleSlice(); private static final WritableSlice<CallKey, OverloadResolutionResultsImpl<VariableDescriptor>> RESOLUTION_RESULTS_FOR_PROPERTY = Slices.createSimpleSlice();
private static final WritableSlice<JetExpression, DelegatingBindingTrace> TRACE_DELTAS_CACHE = Slices.createSimpleSlice(); private static final WritableSlice<CallKey, DelegatingBindingTrace> TRACE_DELTAS_CACHE = Slices.createSimpleSlice();
private static final WritableSlice<JetExpression, CallCandidateResolutionContext<FunctionDescriptor>> DEFERRED_COMPUTATION_FOR_CALL = Slices.createSimpleSlice(); private static final WritableSlice<CallKey, CallCandidateResolutionContext<FunctionDescriptor>> DEFERRED_COMPUTATION_FOR_CALL = Slices.createSimpleSlice();
private final BindingTrace trace = new BindingTraceContext(); private final BindingTrace trace = new BindingTraceContext();
@@ -62,27 +58,27 @@ public class ResolutionResultsCache {
return trace.get(getSliceByMemberType(memberType), callKey); return trace.get(getSliceByMemberType(memberType), callKey);
} }
public void recordResolutionTrace(@NotNull JetExpression expression, @NotNull DelegatingBindingTrace delegatingTrace) { public void recordResolutionTrace(@NotNull CallKey callKey, @NotNull DelegatingBindingTrace delegatingTrace) {
trace.record(TRACE_DELTAS_CACHE, expression, delegatingTrace); trace.record(TRACE_DELTAS_CACHE, callKey, delegatingTrace);
} }
@Nullable @Nullable
public DelegatingBindingTrace getResolutionTrace(@NotNull JetExpression expression) { public DelegatingBindingTrace getResolutionTrace(@NotNull CallKey callKey) {
return trace.get(TRACE_DELTAS_CACHE, expression); return trace.get(TRACE_DELTAS_CACHE, callKey);
} }
public <D extends CallableDescriptor> void recordDeferredComputationForCall( public <D extends CallableDescriptor> void recordDeferredComputationForCall(
@NotNull JetExpression expression, @NotNull CallKey callKey,
@NotNull CallCandidateResolutionContext<D> deferredComputation, @NotNull CallCandidateResolutionContext<D> deferredComputation,
@NotNull MemberType memberType @NotNull MemberType memberType
) { ) {
if (memberType == PROPERTY_MEMBER_TYPE) return; if (memberType == PROPERTY_MEMBER_TYPE) return;
trace.record(DEFERRED_COMPUTATION_FOR_CALL, expression, (CallCandidateResolutionContext<FunctionDescriptor>) deferredComputation); trace.record(DEFERRED_COMPUTATION_FOR_CALL, callKey, (CallCandidateResolutionContext<FunctionDescriptor>) deferredComputation);
} }
@Nullable @Nullable
public CallCandidateResolutionContext<FunctionDescriptor> getDeferredComputation(@NotNull JetExpression expression) { public CallCandidateResolutionContext<FunctionDescriptor> getDeferredComputation(@NotNull CallKey callKey) {
return trace.get(DEFERRED_COMPUTATION_FOR_CALL, expression); return trace.get(DEFERRED_COMPUTATION_FOR_CALL, callKey);
} }
@NotNull @NotNull