@Nullable
  private ResolvedCall<FunctionDescriptor> getResolvedCallForFunction(
      @NotNull Call call,
      @NotNull JetExpression callExpression,
      @NotNull ReceiverValue receiver,
      @NotNull ResolutionContext context,
      @NotNull ResolveMode resolveMode,
      @NotNull boolean[] result) {

    CallResolver callResolver = expressionTypingServices.getCallResolver();
    OverloadResolutionResults<FunctionDescriptor> results =
        callResolver.resolveFunctionCall(
            BasicCallResolutionContext.create(context, call, resolveMode));
    if (!results.isNothing()) {
      checkSuper(receiver, results, context.trace, callExpression);
      result[0] = true;
      if (results.isSingleResult() && resolveMode == ResolveMode.TOP_LEVEL_CALL) {
        if (CallResolverUtil.hasReturnTypeDependentOnNotInferredParams(
            results.getResultingCall())) {
          return null;
        }
      }
      return results.isSingleResult() ? results.getResultingCall() : null;
    }
    result[0] = false;
    return null;
  }
Пример #2
0
  private static <F extends CallableDescriptor> void cacheResults(
      @NotNull ResolutionResultsCache.MemberType<F> memberType,
      @NotNull BasicCallResolutionContext context,
      @NotNull OverloadResolutionResultsImpl<F> results,
      @NotNull DelegatingBindingTrace traceToResolveCall,
      @NotNull TracingStrategy tracing) {
    CallKey callKey = CallResolverUtil.createCallKey(context);
    if (callKey == null) return;

    DelegatingBindingTrace deltasTraceToCacheResolve =
        new DelegatingBindingTrace(
            new BindingTraceContext().getBindingContext(),
            "delta trace for caching resolve of",
            context.call);
    traceToResolveCall.addAllMyDataTo(deltasTraceToCacheResolve);

    context.resolutionResultsCache.recordResolutionResults(callKey, memberType, results);
    context.resolutionResultsCache.recordResolutionTrace(callKey, deltasTraceToCacheResolve);

    if (results.isSingleResult() && memberType == ResolutionResultsCache.FUNCTION_MEMBER_TYPE) {
      CallCandidateResolutionContext<F> callCandidateResolutionContext =
          CallCandidateResolutionContext.createForCallBeingAnalyzed(
              results.getResultingCall().getCallToCompleteTypeArgumentInference(),
              context,
              tracing);
      context.resolutionResultsCache.recordDeferredComputationForCall(
          callKey, callCandidateResolutionContext, memberType);
    }
  }
Пример #3
0
  private <D extends CallableDescriptor, F extends D>
      OverloadResolutionResultsImpl<F> doResolveCallOrGetCachedResults(
          @NotNull ResolutionResultsCache.MemberType<F> memberType,
          @NotNull BasicCallResolutionContext context,
          @NotNull List<ResolutionTask<D, F>> prioritizedTasks,
          @NotNull CallTransformer<D, F> callTransformer,
          @NotNull JetReferenceExpression reference) {
    OverloadResolutionResultsImpl<F> results = null;
    TracingStrategy tracing =
        prioritizedTasks.isEmpty()
            ? TracingStrategy.EMPTY
            : prioritizedTasks.iterator().next().tracing;
    TemporaryBindingTrace traceToResolveCall =
        TemporaryBindingTrace.create(context.trace, "trace to resolve call", context.call);
    CallKey callKey = CallResolverUtil.createCallKey(context);
    if (callKey != null) {
      OverloadResolutionResultsImpl<F> cachedResults =
          context.resolutionResultsCache.getResolutionResults(callKey, memberType);
      if (cachedResults != null) {
        DelegatingBindingTrace deltasTraceForResolve =
            context.resolutionResultsCache.getResolutionTrace(callKey);
        assert deltasTraceForResolve != null;
        deltasTraceForResolve.addAllMyDataTo(traceToResolveCall);
        results = cachedResults;
      }
    }
    if (results == null) {
      BasicCallResolutionContext newContext = context.replaceBindingTrace(traceToResolveCall);
      results = doResolveCall(newContext, prioritizedTasks, callTransformer, reference);
      DelegatingBindingTrace deltasTraceForTypeInference =
          ((OverloadResolutionResultsImpl) results).getTrace();
      if (deltasTraceForTypeInference != null) {
        deltasTraceForTypeInference.addAllMyDataTo(traceToResolveCall);
      }
      completeTypeInferenceDependentOnFunctionLiterals(newContext, results, tracing);
      cacheResults(memberType, context, results, traceToResolveCall, tracing);
    }
    traceToResolveCall.commit();

    if (!prioritizedTasks.isEmpty() && context.contextDependency == ContextDependency.INDEPENDENT) {
      results = completeTypeInferenceDependentOnExpectedType(context, results, tracing);
    }

    if (extension != null) {
      extension.run(results, context);
    }

    return results;
  }
Пример #4
0
  private <D extends CallableDescriptor>
      OverloadResolutionResultsImpl<D> completeTypeInferenceDependentOnExpectedType(
          @NotNull BasicCallResolutionContext context,
          @NotNull OverloadResolutionResultsImpl<D> results,
          @NotNull TracingStrategy tracing) {
    if (results.isSingleResult()) {
      argumentTypeResolver.checkUnmappedArgumentTypes(
          context,
          results
              .getResultingCall()
              .getCallToCompleteTypeArgumentInference()
              .getUnmappedArguments());
    }

    if (!results.isSingleResult()) return results;

    ResolvedCallImpl<D> resolvedCall =
        results.getResultingCall().getCallToCompleteTypeArgumentInference();

    if (!resolvedCall.hasIncompleteTypeParameters()) {
      CallCandidateResolutionContext<D> callCandidateResolutionContext =
          CallCandidateResolutionContext.createForCallBeingAnalyzed(resolvedCall, context, tracing);
      candidateResolver.completeNestedCallsInference(callCandidateResolutionContext);
      candidateResolver.checkValueArgumentTypes(callCandidateResolutionContext);
      return results;
    }
    ResolvedCallImpl<D> copy = CallResolverUtil.copy(resolvedCall, context);
    CallCandidateResolutionContext<D> callCandidateResolutionContext =
        CallCandidateResolutionContext.createForCallBeingAnalyzed(copy, context, tracing);
    candidateResolver.completeTypeInferenceDependentOnExpectedTypeForCall(
        callCandidateResolutionContext, false);

    if (copy.getStatus().isSuccess()) {
      return OverloadResolutionResultsImpl.success(copy);
    }
    return OverloadResolutionResultsImpl.incompleteTypeInference(copy);
  }