001    /*
002     * Copyright 2010-2013 JetBrains s.r.o.
003     *
004     * Licensed under the Apache License, Version 2.0 (the "License");
005     * you may not use this file except in compliance with the License.
006     * You may obtain a copy of the License at
007     *
008     * http://www.apache.org/licenses/LICENSE-2.0
009     *
010     * Unless required by applicable law or agreed to in writing, software
011     * distributed under the License is distributed on an "AS IS" BASIS,
012     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013     * See the License for the specific language governing permissions and
014     * limitations under the License.
015     */
016    
017    package org.jetbrains.jet.lang.types.expressions;
018    
019    import org.jetbrains.annotations.NotNull;
020    import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
021    import org.jetbrains.jet.lang.psi.Call;
022    import org.jetbrains.jet.lang.psi.JetReferenceExpression;
023    import org.jetbrains.jet.lang.resolve.BindingTrace;
024    import org.jetbrains.jet.lang.resolve.calls.autocasts.DataFlowInfo;
025    import org.jetbrains.jet.lang.resolve.calls.context.*;
026    import org.jetbrains.jet.lang.resolve.calls.results.OverloadResolutionResults;
027    import org.jetbrains.jet.lang.resolve.constants.CompileTimeConstantResolver;
028    import org.jetbrains.jet.lang.resolve.name.Name;
029    import org.jetbrains.jet.lang.resolve.scopes.JetScope;
030    import org.jetbrains.jet.lang.types.JetType;
031    
032    public class ExpressionTypingContext extends ResolutionContext<ExpressionTypingContext> {
033    
034        @NotNull
035        public static ExpressionTypingContext newContext(
036                @NotNull ExpressionTypingServices expressionTypingServices,
037                @NotNull BindingTrace trace,
038                @NotNull JetScope scope,
039                @NotNull DataFlowInfo dataFlowInfo,
040                @NotNull JetType expectedType,
041                @NotNull ExpressionPosition expressionPosition
042        ) {
043            return newContext(expressionTypingServices, trace, scope, dataFlowInfo, expectedType, expressionPosition,
044                              ContextDependency.INDEPENDENT, ResolutionResultsCacheImpl.create(), LabelResolver.create()
045            );
046        }
047    
048        @NotNull
049        public static ExpressionTypingContext newContext(
050                @NotNull ExpressionTypingServices expressionTypingServices,
051                @NotNull ResolutionContext resolutionContext
052        ) {
053            return newContext(expressionTypingServices, resolutionContext.trace, resolutionContext.scope, resolutionContext.dataFlowInfo,
054                              resolutionContext.expectedType, resolutionContext.expressionPosition, resolutionContext.contextDependency,
055                              resolutionContext.resolutionResultsCache, resolutionContext.labelResolver
056            );
057        }
058    
059        @NotNull
060        public static ExpressionTypingContext newContext(
061                @NotNull ExpressionTypingServices expressionTypingServices,
062                @NotNull BindingTrace trace,
063                @NotNull JetScope scope,
064                @NotNull DataFlowInfo dataFlowInfo,
065                @NotNull JetType expectedType,
066                @NotNull ExpressionPosition expressionPosition,
067                @NotNull ContextDependency contextDependency,
068                @NotNull ResolutionResultsCache resolutionResultsCache,
069                @NotNull LabelResolver labelResolver
070        ) {
071            return new ExpressionTypingContext(
072                    expressionTypingServices, labelResolver, trace, scope, dataFlowInfo, expectedType, expressionPosition, contextDependency, resolutionResultsCache);
073        }
074    
075        public final ExpressionTypingServices expressionTypingServices;
076    
077        private CompileTimeConstantResolver compileTimeConstantResolver;
078    
079        private ExpressionTypingContext(
080                @NotNull ExpressionTypingServices expressionTypingServices,
081                @NotNull LabelResolver labelResolver,
082                @NotNull BindingTrace trace,
083                @NotNull JetScope scope,
084                @NotNull DataFlowInfo dataFlowInfo,
085                @NotNull JetType expectedType,
086                @NotNull ExpressionPosition expressionPosition,
087                @NotNull ContextDependency contextDependency,
088                @NotNull ResolutionResultsCache resolutionResultsCache
089        ) {
090            super(trace, scope, expectedType, dataFlowInfo, expressionPosition, contextDependency, resolutionResultsCache, labelResolver);
091            this.expressionTypingServices = expressionTypingServices;
092        }
093    
094        @Override
095        protected ExpressionTypingContext create(
096                @NotNull BindingTrace trace,
097                @NotNull JetScope scope,
098                @NotNull DataFlowInfo dataFlowInfo,
099                @NotNull JetType expectedType,
100                @NotNull ExpressionPosition expressionPosition,
101                @NotNull ContextDependency contextDependency,
102                @NotNull ResolutionResultsCache resolutionResultsCache,
103                @NotNull LabelResolver labelResolver
104        ) {
105            return new ExpressionTypingContext(expressionTypingServices, this.labelResolver, trace, scope, dataFlowInfo, expectedType,
106                                               expressionPosition, contextDependency, resolutionResultsCache);
107        }
108    
109        @Override
110        protected ExpressionTypingContext self() {
111            return this;
112        }
113    
114    ///////////// LAZY ACCESSORS
115    
116        public CompileTimeConstantResolver getCompileTimeConstantResolver() {
117            if (compileTimeConstantResolver == null) {
118                compileTimeConstantResolver = new CompileTimeConstantResolver();
119            }
120            return compileTimeConstantResolver;
121        }
122    
123    ////////// Call resolution utilities
124    
125        @NotNull
126        public OverloadResolutionResults<FunctionDescriptor> resolveCallWithGivenName(@NotNull Call call, @NotNull JetReferenceExpression functionReference, @NotNull Name name) {
127            return expressionTypingServices.getCallResolver().resolveCallWithGivenName(
128                    BasicCallResolutionContext.create(this, call, CheckValueArgumentsMode.ENABLED),
129                    functionReference,
130                    name
131            );
132        }
133    }