001 /*
002 * Copyright 2010-2014 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.resolve;
018
019 import com.google.common.collect.Lists;
020 import com.google.common.collect.Maps;
021 import com.google.common.collect.Sets;
022 import com.intellij.lang.ASTNode;
023 import com.intellij.psi.PsiElement;
024 import com.intellij.psi.tree.IElementType;
025 import com.intellij.psi.util.PsiTreeUtil;
026 import kotlin.Function0;
027 import org.jetbrains.annotations.NotNull;
028 import org.jetbrains.annotations.Nullable;
029 import org.jetbrains.jet.lang.descriptors.*;
030 import org.jetbrains.jet.lang.descriptors.annotations.Annotations;
031 import org.jetbrains.jet.lang.descriptors.impl.*;
032 import org.jetbrains.jet.lang.diagnostics.DiagnosticFactory1;
033 import org.jetbrains.jet.lang.evaluate.ConstantExpressionEvaluator;
034 import org.jetbrains.jet.lang.evaluate.EvaluatePackage;
035 import org.jetbrains.jet.lang.psi.*;
036 import org.jetbrains.jet.lang.resolve.calls.autocasts.DataFlowInfo;
037 import org.jetbrains.jet.lang.resolve.constants.CompileTimeConstant;
038 import org.jetbrains.jet.lang.resolve.constants.IntegerValueTypeConstant;
039 import org.jetbrains.jet.lang.resolve.name.FqName;
040 import org.jetbrains.jet.lang.resolve.name.Name;
041 import org.jetbrains.jet.lang.resolve.scopes.JetScope;
042 import org.jetbrains.jet.lang.resolve.scopes.JetScopeUtils;
043 import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
044 import org.jetbrains.jet.lang.resolve.scopes.WritableScopeImpl;
045 import org.jetbrains.jet.lang.types.*;
046 import org.jetbrains.jet.lang.types.checker.JetTypeChecker;
047 import org.jetbrains.jet.lang.types.expressions.ExpressionTypingServices;
048 import org.jetbrains.jet.lang.types.lang.KotlinBuiltIns;
049 import org.jetbrains.jet.lexer.JetKeywordToken;
050 import org.jetbrains.jet.lexer.JetModifierKeywordToken;
051 import org.jetbrains.jet.lexer.JetTokens;
052 import org.jetbrains.jet.storage.StorageManager;
053
054 import javax.inject.Inject;
055 import java.util.*;
056
057 import static org.jetbrains.jet.lang.descriptors.ReceiverParameterDescriptor.NO_RECEIVER_PARAMETER;
058 import static org.jetbrains.jet.lang.diagnostics.Errors.*;
059 import static org.jetbrains.jet.lang.resolve.BindingContext.*;
060 import static org.jetbrains.jet.lang.resolve.DescriptorUtils.*;
061 import static org.jetbrains.jet.lang.resolve.ModifiersChecker.*;
062 import static org.jetbrains.jet.lexer.JetTokens.OVERRIDE_KEYWORD;
063 import static org.jetbrains.jet.storage.LockBasedStorageManager.NO_LOCKS;
064
065 public class DescriptorResolver {
066 public static final Name COPY_METHOD_NAME = Name.identifier("copy");
067 public static final String COMPONENT_FUNCTION_NAME_PREFIX = "component";
068
069 @NotNull
070 private TypeResolver typeResolver;
071 @NotNull
072 private AnnotationResolver annotationResolver;
073 @NotNull
074 private ExpressionTypingServices expressionTypingServices;
075 @NotNull
076 private DelegatedPropertyResolver delegatedPropertyResolver;
077 @NotNull
078 private StorageManager storageManager;
079
080 @Inject
081 public void setTypeResolver(@NotNull TypeResolver typeResolver) {
082 this.typeResolver = typeResolver;
083 }
084
085 @Inject
086 public void setAnnotationResolver(@NotNull AnnotationResolver annotationResolver) {
087 this.annotationResolver = annotationResolver;
088 }
089
090 @Inject
091 public void setExpressionTypingServices(@NotNull ExpressionTypingServices expressionTypingServices) {
092 this.expressionTypingServices = expressionTypingServices;
093 }
094
095 @Inject
096 public void setDelegatedPropertyResolver(@NotNull DelegatedPropertyResolver delegatedPropertyResolver) {
097 this.delegatedPropertyResolver = delegatedPropertyResolver;
098 }
099
100 @Inject
101 public void setStorageManager(@NotNull StorageManager storageManager) {
102 this.storageManager = storageManager;
103 }
104
105 public void resolveMutableClassDescriptor(
106 @NotNull TopDownAnalysisParameters topDownAnalysisParameters,
107 @NotNull JetClass classElement,
108 @NotNull MutableClassDescriptor descriptor,
109 BindingTrace trace
110 ) {
111 // TODO : Where-clause
112 List<TypeParameterDescriptor> typeParameters = Lists.newArrayList();
113 int index = 0;
114 for (JetTypeParameter typeParameter : classElement.getTypeParameters()) {
115 if (!topDownAnalysisParameters.isLazyTopDownAnalysis()) {
116 // TODO: Support
117 AnnotationResolver.reportUnsupportedAnnotationForTypeParameter(typeParameter, trace);
118 }
119
120 TypeParameterDescriptor typeParameterDescriptor = TypeParameterDescriptorImpl.createForFurtherModification(
121 descriptor,
122 Annotations.EMPTY,
123 typeParameter.hasModifier(JetTokens.REIFIED_KEYWORD),
124 typeParameter.getVariance(),
125 JetPsiUtil.safeName(typeParameter.getName()),
126 index
127 );
128 trace.record(BindingContext.TYPE_PARAMETER, typeParameter, typeParameterDescriptor);
129 typeParameters.add(typeParameterDescriptor);
130 index++;
131 }
132 descriptor.setTypeParameterDescriptors(typeParameters);
133 Modality defaultModality = descriptor.getKind() == ClassKind.TRAIT ? Modality.ABSTRACT : Modality.FINAL;
134 descriptor.setModality(resolveModalityFromModifiers(classElement, defaultModality));
135 descriptor.setVisibility(resolveVisibilityFromModifiers(classElement, getDefaultClassVisibility(descriptor)));
136
137 trace.record(BindingContext.CLASS, classElement, descriptor);
138 }
139
140 public void resolveSupertypesForMutableClassDescriptor(
141 @NotNull JetClassOrObject jetClass,
142 @NotNull MutableClassDescriptor descriptor,
143 BindingTrace trace
144 ) {
145 for (JetType supertype : resolveSupertypes(descriptor.getScopeForClassHeaderResolution(), descriptor, jetClass, trace)) {
146 descriptor.addSupertype(supertype);
147 }
148 }
149
150 public List<JetType> resolveSupertypes(
151 @NotNull JetScope scope,
152 @NotNull ClassDescriptor classDescriptor,
153 @NotNull JetClassOrObject jetClass,
154 BindingTrace trace
155 ) {
156 List<JetType> supertypes = Lists.newArrayList();
157 List<JetDelegationSpecifier> delegationSpecifiers = jetClass.getDelegationSpecifiers();
158 Collection<JetType> declaredSupertypes = resolveDelegationSpecifiers(
159 scope,
160 delegationSpecifiers,
161 typeResolver, trace, false);
162
163 for (JetType declaredSupertype : declaredSupertypes) {
164 addValidSupertype(supertypes, declaredSupertype);
165 }
166
167 if (classDescriptor.getKind() == ClassKind.ENUM_CLASS && !containsClass(supertypes)) {
168 supertypes.add(0, KotlinBuiltIns.getInstance().getEnumType(classDescriptor.getDefaultType()));
169 }
170
171 if (supertypes.isEmpty()) {
172 JetType defaultSupertype = getDefaultSupertype(jetClass, trace);
173 addValidSupertype(supertypes, defaultSupertype);
174 }
175
176 return supertypes;
177 }
178
179 private static void addValidSupertype(List<JetType> supertypes, JetType declaredSupertype) {
180 if (!declaredSupertype.isError()) {
181 supertypes.add(declaredSupertype);
182 }
183 }
184
185 private boolean containsClass(Collection<JetType> result) {
186 for (JetType type : result) {
187 ClassifierDescriptor descriptor = type.getConstructor().getDeclarationDescriptor();
188 if (descriptor instanceof ClassDescriptor && ((ClassDescriptor) descriptor).getKind() != ClassKind.TRAIT) {
189 return true;
190 }
191 }
192 return false;
193 }
194
195 private JetType getDefaultSupertype(JetClassOrObject jetClass, BindingTrace trace) {
196 // TODO : beautify
197 if (jetClass instanceof JetEnumEntry) {
198 JetClassOrObject parent = PsiTreeUtil.getParentOfType(jetClass, JetClassOrObject.class);
199 ClassDescriptor parentDescriptor = trace.getBindingContext().get(BindingContext.CLASS, parent);
200 if (parentDescriptor.getTypeConstructor().getParameters().isEmpty()) {
201 return parentDescriptor.getDefaultType();
202 }
203 else {
204 trace.report(NO_GENERICS_IN_SUPERTYPE_SPECIFIER.on(jetClass.getNameIdentifier()));
205 return ErrorUtils.createErrorType("Supertype not specified");
206 }
207 }
208 else if (jetClass instanceof JetClass && ((JetClass) jetClass).isAnnotation()) {
209 return KotlinBuiltIns.getInstance().getAnnotationType();
210 }
211 return KotlinBuiltIns.getInstance().getAnyType();
212 }
213
214 public Collection<JetType> resolveDelegationSpecifiers(
215 JetScope extensibleScope,
216 List<JetDelegationSpecifier> delegationSpecifiers,
217 @NotNull TypeResolver resolver,
218 BindingTrace trace,
219 boolean checkBounds
220 ) {
221 if (delegationSpecifiers.isEmpty()) {
222 return Collections.emptyList();
223 }
224 Collection<JetType> result = Lists.newArrayList();
225 for (JetDelegationSpecifier delegationSpecifier : delegationSpecifiers) {
226 JetTypeReference typeReference = delegationSpecifier.getTypeReference();
227 if (typeReference != null) {
228 result.add(resolver.resolveType(extensibleScope, typeReference, trace, checkBounds));
229 JetTypeElement bareSuperType = checkNullableSupertypeAndStripQuestionMarks(trace, typeReference.getTypeElement());
230 checkProjectionsInImmediateArguments(trace, bareSuperType);
231 }
232 else {
233 result.add(ErrorUtils.createErrorType("No type reference"));
234 }
235 }
236 return result;
237 }
238
239 @Nullable
240 private static JetTypeElement checkNullableSupertypeAndStripQuestionMarks(@NotNull BindingTrace trace, @Nullable JetTypeElement typeElement) {
241 while (typeElement instanceof JetNullableType) {
242 JetNullableType nullableType = (JetNullableType) typeElement;
243 typeElement = nullableType.getInnerType();
244 // report only for innermost '?', the rest gets a 'redundant' warning
245 if (!(typeElement instanceof JetNullableType) && typeElement != null) {
246 trace.report(NULLABLE_SUPERTYPE.on(nullableType));
247 }
248 }
249 return typeElement;
250 }
251
252 private static void checkProjectionsInImmediateArguments(@NotNull BindingTrace trace, @Nullable JetTypeElement typeElement) {
253 if (typeElement instanceof JetUserType) {
254 JetUserType userType = (JetUserType) typeElement;
255 List<JetTypeProjection> typeArguments = userType.getTypeArguments();
256 for (JetTypeProjection typeArgument : typeArguments) {
257 if (typeArgument.getProjectionKind() != JetProjectionKind.NONE) {
258 trace.report(PROJECTION_IN_IMMEDIATE_ARGUMENT_TO_SUPERTYPE.on(typeArgument));
259 }
260 }
261 }
262 }
263
264 @NotNull
265 public SimpleFunctionDescriptor resolveFunctionDescriptorWithAnnotationArguments(
266 @NotNull DeclarationDescriptor containingDescriptor,
267 @NotNull JetScope scope,
268 @NotNull JetNamedFunction function,
269 @NotNull BindingTrace trace,
270 @NotNull DataFlowInfo dataFlowInfo
271 ) {
272 return resolveFunctionDescriptor(containingDescriptor, scope, function, trace, dataFlowInfo,
273 annotationResolver.resolveAnnotationsWithArguments(scope, function.getModifierList(), trace));
274 }
275
276 @NotNull
277 public SimpleFunctionDescriptor resolveFunctionDescriptor(
278 @NotNull DeclarationDescriptor containingDescriptor,
279 @NotNull JetScope scope,
280 @NotNull JetNamedFunction function,
281 @NotNull BindingTrace trace,
282 @NotNull DataFlowInfo dataFlowInfo
283 ) {
284 return resolveFunctionDescriptor(containingDescriptor, scope, function, trace, dataFlowInfo,
285 annotationResolver.resolveAnnotationsWithoutArguments(scope, function.getModifierList(), trace));
286 }
287
288 @NotNull
289 private SimpleFunctionDescriptor resolveFunctionDescriptor(
290 @NotNull DeclarationDescriptor containingDescriptor,
291 @NotNull final JetScope scope,
292 @NotNull final JetNamedFunction function,
293 @NotNull final BindingTrace trace,
294 @NotNull final DataFlowInfo dataFlowInfo,
295 @NotNull Annotations annotations
296 ) {
297 final SimpleFunctionDescriptorImpl functionDescriptor = SimpleFunctionDescriptorImpl.create(
298 containingDescriptor,
299 annotations,
300 JetPsiUtil.safeName(function.getName()),
301 CallableMemberDescriptor.Kind.DECLARATION
302 );
303 WritableScope innerScope = new WritableScopeImpl(scope, functionDescriptor, new TraceBasedRedeclarationHandler(trace),
304 "Function descriptor header scope");
305 innerScope.addLabeledDeclaration(functionDescriptor);
306
307 List<TypeParameterDescriptorImpl> typeParameterDescriptors =
308 resolveTypeParametersForCallableDescriptor(functionDescriptor, innerScope, function.getTypeParameters(), trace);
309 innerScope.changeLockLevel(WritableScope.LockLevel.BOTH);
310 resolveGenericBounds(function, functionDescriptor, innerScope, typeParameterDescriptors, trace);
311
312 JetType receiverType = null;
313 JetTypeReference receiverTypeRef = function.getReceiverTypeRef();
314 if (receiverTypeRef != null) {
315 JetScope scopeForReceiver =
316 function.hasTypeParameterListBeforeFunctionName()
317 ? innerScope
318 : scope;
319 receiverType = typeResolver.resolveType(scopeForReceiver, receiverTypeRef, trace, true);
320 }
321
322 List<ValueParameterDescriptor> valueParameterDescriptors =
323 resolveValueParameters(functionDescriptor, innerScope, function.getValueParameters(), trace);
324
325 innerScope.changeLockLevel(WritableScope.LockLevel.READING);
326
327 JetTypeReference returnTypeRef = function.getReturnTypeRef();
328 JetType returnType;
329 if (returnTypeRef != null) {
330 returnType = typeResolver.resolveType(innerScope, returnTypeRef, trace, true);
331 }
332 else if (function.hasBlockBody()) {
333 returnType = KotlinBuiltIns.getInstance().getUnitType();
334 }
335 else {
336 JetExpression bodyExpression = function.getBodyExpression();
337 if (bodyExpression != null) {
338 returnType =
339 DeferredType.createRecursionIntolerant(
340 storageManager,
341 trace,
342 new Function0<JetType>() {
343 @Override
344 public JetType invoke() {
345 JetType type = expressionTypingServices
346 .getBodyExpressionType(trace, scope, dataFlowInfo, function, functionDescriptor);
347 return transformAnonymousTypeIfNeeded(functionDescriptor, function, type, trace);
348 }
349 });
350 }
351 else {
352 returnType = ErrorUtils.createErrorType("No type, no body");
353 }
354 }
355 boolean hasBody = function.getBodyExpression() != null;
356 Modality modality = resolveModalityFromModifiers(function, getDefaultModality(containingDescriptor, hasBody));
357 Visibility visibility = resolveVisibilityFromModifiers(function, getDefaultVisibility(function, containingDescriptor));
358 functionDescriptor.initialize(
359 receiverType,
360 getExpectedThisObjectIfNeeded(containingDescriptor),
361 typeParameterDescriptors,
362 valueParameterDescriptors,
363 returnType,
364 modality,
365 visibility
366 );
367
368 BindingContextUtils.recordFunctionDeclarationToDescriptor(trace, function, functionDescriptor);
369 return functionDescriptor;
370 }
371
372 @NotNull
373 public static SimpleFunctionDescriptor createComponentFunctionDescriptor(
374 int parameterIndex,
375 @NotNull PropertyDescriptor property,
376 @NotNull ValueParameterDescriptor parameter,
377 @NotNull ClassDescriptor classDescriptor,
378 @NotNull BindingTrace trace
379 ) {
380 String functionName = COMPONENT_FUNCTION_NAME_PREFIX + parameterIndex;
381 JetType returnType = property.getType();
382
383 SimpleFunctionDescriptorImpl functionDescriptor = SimpleFunctionDescriptorImpl.create(
384 classDescriptor,
385 Annotations.EMPTY,
386 Name.identifier(functionName),
387 CallableMemberDescriptor.Kind.SYNTHESIZED
388 );
389
390 functionDescriptor.initialize(
391 null,
392 classDescriptor.getThisAsReceiverParameter(),
393 Collections.<TypeParameterDescriptor>emptyList(),
394 Collections.<ValueParameterDescriptor>emptyList(),
395 returnType,
396 Modality.FINAL,
397 property.getVisibility()
398 );
399
400 trace.record(BindingContext.DATA_CLASS_COMPONENT_FUNCTION, parameter, functionDescriptor);
401
402 return functionDescriptor;
403 }
404
405 @NotNull
406 public static SimpleFunctionDescriptor createCopyFunctionDescriptor(
407 @NotNull Collection<ValueParameterDescriptor> constructorParameters,
408 @NotNull ClassDescriptor classDescriptor,
409 @NotNull BindingTrace trace
410 ) {
411 JetType returnType = classDescriptor.getDefaultType();
412
413 SimpleFunctionDescriptorImpl functionDescriptor = SimpleFunctionDescriptorImpl.create(
414 classDescriptor,
415 Annotations.EMPTY,
416 COPY_METHOD_NAME,
417 CallableMemberDescriptor.Kind.SYNTHESIZED
418 );
419
420 List<ValueParameterDescriptor> parameterDescriptors = Lists.newArrayList();
421
422 for (ValueParameterDescriptor parameter : constructorParameters) {
423 PropertyDescriptor propertyDescriptor = trace.getBindingContext().get(BindingContext.VALUE_PARAMETER_AS_PROPERTY, parameter);
424 // If parameter hasn't corresponding property, so it mustn't have default value as a parameter in copy function for data class
425 boolean declaresDefaultValue = propertyDescriptor != null;
426 ValueParameterDescriptorImpl parameterDescriptor =
427 new ValueParameterDescriptorImpl(functionDescriptor, null, parameter.getIndex(), parameter.getAnnotations(),
428 parameter.getName(), parameter.getType(),
429 declaresDefaultValue,
430 parameter.getVarargElementType());
431 parameterDescriptors.add(parameterDescriptor);
432 if (declaresDefaultValue) {
433 trace.record(BindingContext.VALUE_PARAMETER_AS_PROPERTY, parameterDescriptor, propertyDescriptor);
434 }
435 }
436
437 functionDescriptor.initialize(
438 null,
439 classDescriptor.getThisAsReceiverParameter(),
440 Collections.<TypeParameterDescriptor>emptyList(),
441 parameterDescriptors,
442 returnType,
443 Modality.FINAL,
444 classDescriptor.getVisibility()
445 );
446
447 trace.record(BindingContext.DATA_CLASS_COPY_FUNCTION, classDescriptor, functionDescriptor);
448 return functionDescriptor;
449 }
450
451 public static Visibility getDefaultVisibility(JetModifierListOwner modifierListOwner, DeclarationDescriptor containingDescriptor) {
452 Visibility defaultVisibility;
453 if (containingDescriptor instanceof ClassDescriptor) {
454 JetModifierList modifierList = modifierListOwner.getModifierList();
455 defaultVisibility = modifierList != null && modifierList.hasModifier(OVERRIDE_KEYWORD)
456 ? Visibilities.INHERITED
457 : Visibilities.INTERNAL;
458 }
459 else if (containingDescriptor instanceof FunctionDescriptor) {
460 defaultVisibility = Visibilities.LOCAL;
461 }
462 else {
463 defaultVisibility = Visibilities.INTERNAL;
464 }
465 return defaultVisibility;
466 }
467
468 public static Modality getDefaultModality(DeclarationDescriptor containingDescriptor, boolean isBodyPresent) {
469 Modality defaultModality;
470 if (containingDescriptor instanceof ClassDescriptor) {
471 boolean isTrait = ((ClassDescriptor) containingDescriptor).getKind() == ClassKind.TRAIT;
472 boolean isDefinitelyAbstract = isTrait && !isBodyPresent;
473 Modality basicModality = isTrait ? Modality.OPEN : Modality.FINAL;
474 defaultModality = isDefinitelyAbstract ? Modality.ABSTRACT : basicModality;
475 }
476 else {
477 defaultModality = Modality.FINAL;
478 }
479 return defaultModality;
480 }
481
482 @NotNull
483 private List<ValueParameterDescriptor> resolveValueParameters(
484 FunctionDescriptor functionDescriptor,
485 WritableScope parameterScope,
486 List<JetParameter> valueParameters,
487 BindingTrace trace
488 ) {
489 List<ValueParameterDescriptor> result = new ArrayList<ValueParameterDescriptor>();
490 for (int i = 0; i < valueParameters.size(); i++) {
491 JetParameter valueParameter = valueParameters.get(i);
492 JetTypeReference typeReference = valueParameter.getTypeReference();
493
494 JetType type;
495 if (typeReference == null) {
496 trace.report(VALUE_PARAMETER_WITH_NO_TYPE_ANNOTATION.on(valueParameter));
497 type = ErrorUtils.createErrorType("Type annotation was missing");
498 }
499 else {
500 type = typeResolver.resolveType(parameterScope, typeReference, trace, true);
501 }
502
503 if (!(functionDescriptor instanceof ConstructorDescriptor)) {
504 checkParameterHasNoValOrVar(trace, valueParameter, VAL_OR_VAR_ON_FUN_PARAMETER);
505 checkParameterHasNoModifier(trace, valueParameter);
506 } else {
507 checkConstructorParameterHasNoModifier(trace, valueParameter);
508 }
509
510 ValueParameterDescriptor valueParameterDescriptor =
511 resolveValueParameterDescriptor(parameterScope, functionDescriptor, valueParameter, i, type, trace);
512 parameterScope.addVariableDescriptor(valueParameterDescriptor);
513 result.add(valueParameterDescriptor);
514 }
515 return result;
516 }
517
518 @NotNull
519 public ValueParameterDescriptorImpl resolveValueParameterDescriptor(
520 JetScope scope, DeclarationDescriptor declarationDescriptor,
521 JetParameter valueParameter, int index, JetType type, BindingTrace trace
522 ) {
523 return resolveValueParameterDescriptor(declarationDescriptor, valueParameter, index, type, trace,
524 annotationResolver.resolveAnnotationsWithoutArguments(scope, valueParameter.getModifierList(), trace));
525 }
526
527 @NotNull
528 public ValueParameterDescriptorImpl resolveValueParameterDescriptorWithAnnotationArguments(
529 JetScope scope, DeclarationDescriptor declarationDescriptor,
530 JetParameter valueParameter, int index, JetType type, BindingTrace trace
531 ) {
532 return resolveValueParameterDescriptor(declarationDescriptor, valueParameter, index, type, trace,
533 annotationResolver.resolveAnnotationsWithArguments(scope, valueParameter.getModifierList(), trace));
534 }
535
536 @NotNull
537 private static ValueParameterDescriptorImpl resolveValueParameterDescriptor(
538 DeclarationDescriptor declarationDescriptor,
539 JetParameter valueParameter, int index, JetType type, BindingTrace trace,
540 Annotations annotations
541 ) {
542 JetType varargElementType = null;
543 JetType variableType = type;
544 if (valueParameter.hasModifier(JetTokens.VARARG_KEYWORD)) {
545 varargElementType = type;
546 variableType = DescriptorUtils.getVarargParameterType(type);
547 }
548 ValueParameterDescriptorImpl valueParameterDescriptor = new ValueParameterDescriptorImpl(
549 declarationDescriptor,
550 null,
551 index,
552 annotations,
553 JetPsiUtil.safeName(valueParameter.getName()),
554 variableType,
555 valueParameter.getDefaultValue() != null,
556 varargElementType
557 );
558
559 trace.record(BindingContext.VALUE_PARAMETER, valueParameter, valueParameterDescriptor);
560 return valueParameterDescriptor;
561 }
562
563 public List<TypeParameterDescriptorImpl> resolveTypeParametersForCallableDescriptor(
564 DeclarationDescriptor containingDescriptor,
565 WritableScope extensibleScope,
566 List<JetTypeParameter> typeParameters,
567 BindingTrace trace
568 ) {
569 List<TypeParameterDescriptorImpl> result = new ArrayList<TypeParameterDescriptorImpl>();
570 for (int i = 0, typeParametersSize = typeParameters.size(); i < typeParametersSize; i++) {
571 JetTypeParameter typeParameter = typeParameters.get(i);
572 result.add(resolveTypeParameterForCallableDescriptor(containingDescriptor, extensibleScope, typeParameter, i, trace));
573 }
574 return result;
575 }
576
577 private TypeParameterDescriptorImpl resolveTypeParameterForCallableDescriptor(
578 DeclarationDescriptor containingDescriptor,
579 WritableScope extensibleScope,
580 JetTypeParameter typeParameter,
581 int index,
582 BindingTrace trace
583 ) {
584 if (typeParameter.getVariance() != Variance.INVARIANT) {
585 assert !(containingDescriptor instanceof ClassifierDescriptor) : "This method is intended for functions/properties";
586 trace.report(VARIANCE_ON_TYPE_PARAMETER_OF_FUNCTION_OR_PROPERTY.on(typeParameter));
587 }
588
589 // TODO: Support annotation for type parameters
590 AnnotationResolver.reportUnsupportedAnnotationForTypeParameter(typeParameter, trace);
591
592 TypeParameterDescriptorImpl typeParameterDescriptor = TypeParameterDescriptorImpl.createForFurtherModification(
593 containingDescriptor,
594 Annotations.EMPTY,
595 typeParameter.hasModifier(JetTokens.REIFIED_KEYWORD),
596 typeParameter.getVariance(),
597 JetPsiUtil.safeName(typeParameter.getName()),
598 index
599 );
600 trace.record(BindingContext.TYPE_PARAMETER, typeParameter, typeParameterDescriptor);
601 extensibleScope.addTypeParameterDescriptor(typeParameterDescriptor);
602 return typeParameterDescriptor;
603 }
604
605 @NotNull
606 public static ConstructorDescriptorImpl createAndRecordPrimaryConstructorForObject(
607 @Nullable PsiElement object,
608 @NotNull ClassDescriptor classDescriptor,
609 @NotNull BindingTrace trace
610 ) {
611 ConstructorDescriptorImpl constructorDescriptor = DescriptorFactory.createPrimaryConstructorForObject(classDescriptor);
612 if (object != null) {
613 trace.record(CONSTRUCTOR, object, constructorDescriptor);
614 }
615 return constructorDescriptor;
616 }
617
618 static final class UpperBoundCheckerTask {
619 JetTypeReference upperBound;
620 JetType upperBoundType;
621 boolean isClassObjectConstraint;
622
623 private UpperBoundCheckerTask(JetTypeReference upperBound, JetType upperBoundType, boolean classObjectConstraint) {
624 this.upperBound = upperBound;
625 this.upperBoundType = upperBoundType;
626 isClassObjectConstraint = classObjectConstraint;
627 }
628 }
629
630 public void resolveGenericBounds(
631 @NotNull JetTypeParameterListOwner declaration,
632 @NotNull DeclarationDescriptor descriptor,
633 JetScope scope,
634 List<TypeParameterDescriptorImpl> parameters,
635 BindingTrace trace
636 ) {
637 List<UpperBoundCheckerTask> deferredUpperBoundCheckerTasks = Lists.newArrayList();
638
639 List<JetTypeParameter> typeParameters = declaration.getTypeParameters();
640 Map<Name, TypeParameterDescriptorImpl> parameterByName = Maps.newHashMap();
641 for (int i = 0; i < typeParameters.size(); i++) {
642 JetTypeParameter jetTypeParameter = typeParameters.get(i);
643 TypeParameterDescriptorImpl typeParameterDescriptor = parameters.get(i);
644
645 parameterByName.put(typeParameterDescriptor.getName(), typeParameterDescriptor);
646
647 JetTypeReference extendsBound = jetTypeParameter.getExtendsBound();
648 if (extendsBound != null) {
649 JetType type = typeResolver.resolveType(scope, extendsBound, trace, false);
650 typeParameterDescriptor.addUpperBound(type);
651 deferredUpperBoundCheckerTasks.add(new UpperBoundCheckerTask(extendsBound, type, false));
652 }
653 }
654 for (JetTypeConstraint constraint : declaration.getTypeConstraints()) {
655 reportUnsupportedClassObjectConstraint(trace, constraint);
656
657 JetSimpleNameExpression subjectTypeParameterName = constraint.getSubjectTypeParameterName();
658 if (subjectTypeParameterName == null) {
659 continue;
660 }
661 Name referencedName = subjectTypeParameterName.getReferencedNameAsName();
662 TypeParameterDescriptorImpl typeParameterDescriptor = parameterByName.get(referencedName);
663 JetTypeReference boundTypeReference = constraint.getBoundTypeReference();
664 JetType bound = null;
665 if (boundTypeReference != null) {
666 bound = typeResolver.resolveType(scope, boundTypeReference, trace, false);
667 deferredUpperBoundCheckerTasks
668 .add(new UpperBoundCheckerTask(boundTypeReference, bound, constraint.isClassObjectConstraint()));
669 }
670
671 if (typeParameterDescriptor != null) {
672 trace.record(BindingContext.REFERENCE_TARGET, subjectTypeParameterName, typeParameterDescriptor);
673 if (bound != null) {
674 if (constraint.isClassObjectConstraint()) {
675 // Class object bounds are not supported
676 //typeParameterDescriptor.addClassObjectBound(bound);
677 }
678 else {
679 typeParameterDescriptor.addUpperBound(bound);
680 }
681 }
682 }
683 }
684
685 for (TypeParameterDescriptorImpl parameter : parameters) {
686 parameter.addDefaultUpperBound();
687
688 parameter.setInitialized();
689
690 checkConflictingUpperBounds(trace, parameter, typeParameters.get(parameter.getIndex()));
691 }
692
693 if (!(declaration instanceof JetClass)) {
694 for (UpperBoundCheckerTask checkerTask : deferredUpperBoundCheckerTasks) {
695 checkUpperBoundType(checkerTask.upperBound, checkerTask.upperBoundType, checkerTask.isClassObjectConstraint, trace);
696 }
697
698 checkNamesInConstraints(declaration, descriptor, scope, trace);
699 }
700 }
701
702 public static void checkConflictingUpperBounds(
703 @NotNull BindingTrace trace,
704 @NotNull TypeParameterDescriptor parameter,
705 @NotNull JetTypeParameter typeParameter
706 ) {
707 PsiElement nameIdentifier = typeParameter.getNameIdentifier();
708 if (KotlinBuiltIns.getInstance().isNothing(parameter.getUpperBoundsAsType())) {
709 if (nameIdentifier != null) {
710 trace.report(CONFLICTING_UPPER_BOUNDS.on(nameIdentifier, parameter));
711 }
712 }
713
714 JetType classObjectType = parameter.getClassObjectType();
715 if (classObjectType != null && KotlinBuiltIns.getInstance().isNothing(classObjectType)) {
716 if (nameIdentifier != null) {
717 trace.report(CONFLICTING_CLASS_OBJECT_UPPER_BOUNDS.on(nameIdentifier, parameter));
718 }
719 }
720 }
721
722 public void checkNamesInConstraints(
723 @NotNull JetTypeParameterListOwner declaration,
724 @NotNull DeclarationDescriptor descriptor,
725 @NotNull JetScope scope,
726 @NotNull BindingTrace trace
727 ) {
728 for (JetTypeConstraint constraint : declaration.getTypeConstraints()) {
729 JetSimpleNameExpression nameExpression = constraint.getSubjectTypeParameterName();
730 if (nameExpression == null) continue;
731
732 Name name = nameExpression.getReferencedNameAsName();
733
734 ClassifierDescriptor classifier = scope.getClassifier(name);
735 if (classifier instanceof TypeParameterDescriptor && classifier.getContainingDeclaration() == descriptor) continue;
736
737 if (classifier != null) {
738 // To tell the user that we look only for locally defined type parameters
739 trace.report(NAME_IN_CONSTRAINT_IS_NOT_A_TYPE_PARAMETER.on(nameExpression, constraint, declaration));
740 trace.record(BindingContext.REFERENCE_TARGET, nameExpression, classifier);
741 }
742 else {
743 trace.report(UNRESOLVED_REFERENCE.on(nameExpression, nameExpression));
744 }
745
746 JetTypeReference boundTypeReference = constraint.getBoundTypeReference();
747 if (boundTypeReference != null) {
748 typeResolver.resolveType(scope, boundTypeReference, trace, true);
749 }
750 }
751 }
752
753 public static void reportUnsupportedClassObjectConstraint(BindingTrace trace, JetTypeConstraint constraint) {
754 if (constraint.isClassObjectConstraint()) {
755 trace.report(UNSUPPORTED.on(constraint, "Class objects constraints are not supported yet"));
756 }
757 }
758
759 public static void checkUpperBoundType(
760 JetTypeReference upperBound,
761 JetType upperBoundType,
762 boolean isClassObjectConstraint,
763 BindingTrace trace
764 ) {
765 if (!TypeUtils.canHaveSubtypes(JetTypeChecker.INSTANCE, upperBoundType)) {
766 if (isClassObjectConstraint) {
767 trace.report(FINAL_CLASS_OBJECT_UPPER_BOUND.on(upperBound, upperBoundType));
768 }
769 else {
770 trace.report(FINAL_UPPER_BOUND.on(upperBound, upperBoundType));
771 }
772 }
773 }
774
775 @NotNull
776 public VariableDescriptor resolveLocalVariableDescriptor(
777 @NotNull JetScope scope,
778 @NotNull JetParameter parameter,
779 BindingTrace trace
780 ) {
781 JetType type = resolveParameterType(scope, parameter, trace);
782 return resolveLocalVariableDescriptor(parameter, type, trace, scope);
783 }
784
785 private JetType resolveParameterType(JetScope scope, JetParameter parameter, BindingTrace trace) {
786 JetTypeReference typeReference = parameter.getTypeReference();
787 JetType type;
788 if (typeReference != null) {
789 type = typeResolver.resolveType(scope, typeReference, trace, true);
790 }
791 else {
792 // Error is reported by the parser
793 type = ErrorUtils.createErrorType("Annotation is absent");
794 }
795 if (parameter.hasModifier(JetTokens.VARARG_KEYWORD)) {
796 return DescriptorUtils.getVarargParameterType(type);
797 }
798 return type;
799 }
800
801 public VariableDescriptor resolveLocalVariableDescriptor(
802 @NotNull JetParameter parameter,
803 @NotNull JetType type,
804 BindingTrace trace,
805 @NotNull JetScope scope
806 ) {
807 VariableDescriptor variableDescriptor = new LocalVariableDescriptor(
808 scope.getContainingDeclaration(),
809 annotationResolver.resolveAnnotationsWithArguments(scope, parameter.getModifierList(), trace),
810 JetPsiUtil.safeName(parameter.getName()),
811 type,
812 false);
813 trace.record(BindingContext.VALUE_PARAMETER, parameter, variableDescriptor);
814 return variableDescriptor;
815 }
816
817 @NotNull
818 public VariableDescriptor resolveLocalVariableDescriptor(
819 JetScope scope,
820 JetVariableDeclaration variable,
821 DataFlowInfo dataFlowInfo,
822 BindingTrace trace
823 ) {
824 DeclarationDescriptor containingDeclaration = scope.getContainingDeclaration();
825 // SCRIPT: Create property descriptors
826 if (JetPsiUtil.isScriptDeclaration(variable)) {
827 PropertyDescriptorImpl propertyDescriptor = PropertyDescriptorImpl.create(
828 containingDeclaration,
829 annotationResolver.resolveAnnotationsWithArguments(scope, variable.getModifierList(), trace),
830 Modality.FINAL,
831 Visibilities.INTERNAL,
832 variable.isVar(),
833 JetPsiUtil.safeName(variable.getName()),
834 CallableMemberDescriptor.Kind.DECLARATION
835 );
836
837 JetType type =
838 getVariableType(propertyDescriptor, scope, variable, dataFlowInfo, false, trace); // For a local variable the type must not be deferred
839
840 ReceiverParameterDescriptor receiverParameter = ((ScriptDescriptor) containingDeclaration).getThisAsReceiverParameter();
841 propertyDescriptor.setType(type, Collections.<TypeParameterDescriptor>emptyList(), receiverParameter, (JetType) null);
842 initializeWithDefaultGetterSetter(propertyDescriptor);
843 trace.record(BindingContext.VARIABLE, variable, propertyDescriptor);
844 return propertyDescriptor;
845 }
846 else {
847 VariableDescriptorImpl variableDescriptor =
848 resolveLocalVariableDescriptorWithType(scope, variable, null, trace);
849
850 JetType type =
851 getVariableType(variableDescriptor, scope, variable, dataFlowInfo, false, trace); // For a local variable the type must not be deferred
852 variableDescriptor.setOutType(type);
853 return variableDescriptor;
854 }
855 }
856
857 private static void initializeWithDefaultGetterSetter(PropertyDescriptorImpl propertyDescriptor) {
858 PropertyGetterDescriptorImpl getter = propertyDescriptor.getGetter();
859 if (getter == null && propertyDescriptor.getVisibility() != Visibilities.PRIVATE) {
860 getter = DescriptorFactory.createDefaultGetter(propertyDescriptor);
861 getter.initialize(propertyDescriptor.getType());
862 }
863
864 PropertySetterDescriptor setter = propertyDescriptor.getSetter();
865 if (setter == null && propertyDescriptor.isVar()) {
866 setter = DescriptorFactory.createDefaultSetter(propertyDescriptor);
867 }
868 propertyDescriptor.initialize(getter, setter);
869 }
870
871 @NotNull
872 public VariableDescriptorImpl resolveLocalVariableDescriptorWithType(
873 @NotNull JetScope scope,
874 @NotNull JetVariableDeclaration variable,
875 @Nullable JetType type,
876 @NotNull BindingTrace trace
877 ) {
878 VariableDescriptorImpl variableDescriptor = new LocalVariableDescriptor(
879 scope.getContainingDeclaration(),
880 annotationResolver.resolveAnnotationsWithArguments(scope, variable.getModifierList(), trace),
881 JetPsiUtil.safeName(variable.getName()),
882 type,
883 variable.isVar());
884 trace.record(BindingContext.VARIABLE, variable, variableDescriptor);
885 return variableDescriptor;
886 }
887
888 @NotNull
889 public PropertyDescriptor resolvePropertyDescriptor(
890 @NotNull DeclarationDescriptor containingDeclaration,
891 @NotNull JetScope scope,
892 @NotNull JetProperty property,
893 @NotNull BindingTrace trace,
894 @NotNull DataFlowInfo dataFlowInfo
895 ) {
896 JetModifierList modifierList = property.getModifierList();
897 boolean isVar = property.isVar();
898
899 boolean hasBody = hasBody(property);
900 Modality modality = containingDeclaration instanceof ClassDescriptor
901 ? resolveModalityFromModifiers(property, getDefaultModality(containingDeclaration, hasBody))
902 : Modality.FINAL;
903 Visibility visibility = resolveVisibilityFromModifiers(property, getDefaultVisibility(property, containingDeclaration));
904 PropertyDescriptorImpl propertyDescriptor = PropertyDescriptorImpl.create(
905 containingDeclaration,
906 annotationResolver.resolveAnnotationsWithoutArguments(scope, modifierList, trace),
907 modality,
908 visibility,
909 isVar,
910 JetPsiUtil.safeName(property.getName()),
911 CallableMemberDescriptor.Kind.DECLARATION
912 );
913
914 List<TypeParameterDescriptorImpl> typeParameterDescriptors;
915 JetScope scopeWithTypeParameters;
916 JetType receiverType = null;
917
918 {
919 List<JetTypeParameter> typeParameters = property.getTypeParameters();
920 if (typeParameters.isEmpty()) {
921 scopeWithTypeParameters = scope;
922 typeParameterDescriptors = Collections.emptyList();
923 }
924 else {
925 WritableScope writableScope = new WritableScopeImpl(
926 scope, containingDeclaration, new TraceBasedRedeclarationHandler(trace),
927 "Scope with type parameters of a property");
928 typeParameterDescriptors = resolveTypeParametersForCallableDescriptor(containingDeclaration, writableScope, typeParameters,
929 trace);
930 writableScope.changeLockLevel(WritableScope.LockLevel.READING);
931 resolveGenericBounds(property, propertyDescriptor, writableScope, typeParameterDescriptors, trace);
932 scopeWithTypeParameters = writableScope;
933 }
934
935 JetTypeReference receiverTypeRef = property.getReceiverTypeRef();
936 if (receiverTypeRef != null) {
937 receiverType = typeResolver.resolveType(scopeWithTypeParameters, receiverTypeRef, trace, true);
938 }
939 }
940
941 ReceiverParameterDescriptor receiverDescriptor = DescriptorFactory.createReceiverParameterForCallable(propertyDescriptor,
942 receiverType);
943
944 JetScope propertyScope = JetScopeUtils.getPropertyDeclarationInnerScope(propertyDescriptor, scope, typeParameterDescriptors,
945 NO_RECEIVER_PARAMETER, trace);
946
947 JetType type = getVariableType(propertyDescriptor, propertyScope, property, dataFlowInfo, true, trace);
948
949 propertyDescriptor.setType(type, typeParameterDescriptors, getExpectedThisObjectIfNeeded(containingDeclaration),
950 receiverDescriptor);
951
952 PropertyGetterDescriptorImpl getter = resolvePropertyGetterDescriptor(scopeWithTypeParameters, property, propertyDescriptor, trace);
953 PropertySetterDescriptor setter = resolvePropertySetterDescriptor(scopeWithTypeParameters, property, propertyDescriptor, trace);
954
955 propertyDescriptor.initialize(getter, setter);
956
957 trace.record(BindingContext.VARIABLE, property, propertyDescriptor);
958 return propertyDescriptor;
959 }
960
961 /*package*/
962 static boolean hasBody(JetProperty property) {
963 boolean hasBody = property.getDelegateExpressionOrInitializer() != null;
964 if (!hasBody) {
965 JetPropertyAccessor getter = property.getGetter();
966 if (getter != null && getter.getBodyExpression() != null) {
967 hasBody = true;
968 }
969 JetPropertyAccessor setter = property.getSetter();
970 if (!hasBody && setter != null && setter.getBodyExpression() != null) {
971 hasBody = true;
972 }
973 }
974 return hasBody;
975 }
976
977 @NotNull
978 private JetType getVariableType(
979 @NotNull final VariableDescriptorImpl variableDescriptor,
980 @NotNull final JetScope scope,
981 @NotNull final JetVariableDeclaration variable,
982 @NotNull final DataFlowInfo dataFlowInfo,
983 boolean notLocal,
984 @NotNull final BindingTrace trace
985 ) {
986 JetTypeReference propertyTypeRef = variable.getTypeRef();
987
988 boolean hasDelegate = variable instanceof JetProperty && ((JetProperty) variable).getDelegateExpression() != null;
989 if (propertyTypeRef == null) {
990 final JetExpression initializer = variable.getInitializer();
991 if (initializer == null) {
992 if (hasDelegate && variableDescriptor instanceof PropertyDescriptor) {
993 final JetProperty property = (JetProperty) variable;
994 final JetExpression propertyDelegateExpression = property.getDelegateExpression();
995 if (propertyDelegateExpression != null) {
996 return DeferredType.createRecursionIntolerant(
997 storageManager,
998 trace,
999 new Function0<JetType>() {
1000 @Override
1001 public JetType invoke() {
1002 return resolveDelegatedPropertyType(property, (PropertyDescriptor) variableDescriptor, scope,
1003 propertyDelegateExpression, dataFlowInfo, trace);
1004 }
1005 });
1006 }
1007 }
1008 if (!notLocal) {
1009 trace.report(VARIABLE_WITH_NO_TYPE_NO_INITIALIZER.on(variable));
1010 }
1011 return ErrorUtils.createErrorType("No type, no body");
1012 }
1013 else {
1014 if (notLocal) {
1015 return DeferredType.createRecursionIntolerant(
1016 storageManager,
1017 trace,
1018 new Function0<JetType>() {
1019 @Override
1020 public JetType invoke() {
1021 JetType initializerType = resolveInitializerType(scope, initializer, dataFlowInfo, trace);
1022 setConstantForVariableIfNeeded(variableDescriptor, scope, variable, dataFlowInfo, initializerType, trace);
1023 return transformAnonymousTypeIfNeeded(variableDescriptor, variable, initializerType, trace);
1024 }
1025 }
1026 );
1027 }
1028 else {
1029 JetType initializerType = resolveInitializerType(scope, initializer, dataFlowInfo, trace);
1030 setConstantForVariableIfNeeded(variableDescriptor, scope, variable, dataFlowInfo, initializerType, trace);
1031 return initializerType;
1032 }
1033 }
1034 }
1035 else {
1036 JetType type = typeResolver.resolveType(scope, propertyTypeRef, trace, true);
1037 setConstantForVariableIfNeeded(variableDescriptor, scope, variable, dataFlowInfo, type, trace);
1038 return type;
1039 }
1040 }
1041
1042 private void setConstantForVariableIfNeeded(
1043 @NotNull VariableDescriptorImpl variableDescriptor,
1044 @NotNull final JetScope scope,
1045 @NotNull JetVariableDeclaration variable,
1046 @NotNull final DataFlowInfo dataFlowInfo,
1047 @NotNull final JetType variableType,
1048 @NotNull final BindingTrace trace
1049 ) {
1050 if (!shouldRecordInitializerForProperty(variableDescriptor, variableType)) return;
1051
1052 final JetExpression initializer = variable.getInitializer();
1053 if (initializer == null) return;
1054
1055 variableDescriptor.setCompileTimeInitializer(
1056 storageManager.createRecursionTolerantNullableLazyValue(new Function0<CompileTimeConstant<?>>() {
1057 @Nullable
1058 @Override
1059 public CompileTimeConstant<?> invoke() {
1060 JetType initializerType = expressionTypingServices.safeGetType(scope, initializer, variableType, dataFlowInfo, trace);
1061 CompileTimeConstant<?> constant = ConstantExpressionEvaluator.object$.evaluate(initializer, trace, initializerType);
1062 if (constant instanceof IntegerValueTypeConstant) {
1063 return EvaluatePackage.createCompileTimeConstantWithType((IntegerValueTypeConstant) constant, initializerType);
1064 }
1065 return constant;
1066 }
1067 }, null)
1068 );
1069 }
1070
1071 @NotNull
1072 private JetType resolveDelegatedPropertyType(
1073 @NotNull JetProperty property,
1074 @NotNull PropertyDescriptor propertyDescriptor,
1075 @NotNull JetScope scope,
1076 @NotNull JetExpression delegateExpression,
1077 @NotNull DataFlowInfo dataFlowInfo,
1078 @NotNull BindingTrace trace
1079 ) {
1080 JetScope accessorScope = JetScopeUtils.makeScopeForPropertyAccessor(propertyDescriptor, scope, trace);
1081
1082 JetType type = delegatedPropertyResolver.resolveDelegateExpression(
1083 delegateExpression, property, propertyDescriptor, scope, accessorScope, trace, dataFlowInfo);
1084
1085 if (type != null) {
1086 JetType getterReturnType = delegatedPropertyResolver
1087 .getDelegatedPropertyGetMethodReturnType(propertyDescriptor, delegateExpression, type, trace, accessorScope);
1088 if (getterReturnType != null) {
1089 return getterReturnType;
1090 }
1091 }
1092 return ErrorUtils.createErrorType("Type from delegate");
1093 }
1094
1095 @Nullable
1096 private static JetType transformAnonymousTypeIfNeeded(
1097 @NotNull DeclarationDescriptorWithVisibility descriptor,
1098 @NotNull JetNamedDeclaration declaration,
1099 @NotNull JetType type,
1100 @NotNull BindingTrace trace
1101 ) {
1102 ClassifierDescriptor classifierDescriptor = type.getConstructor().getDeclarationDescriptor();
1103 if (classifierDescriptor == null || !DescriptorUtils.isAnonymousObject(classifierDescriptor)) {
1104 return type;
1105 }
1106
1107 boolean definedInClass = DescriptorUtils.getParentOfType(descriptor, ClassDescriptor.class) != null;
1108 boolean isLocal = descriptor.getContainingDeclaration() instanceof CallableDescriptor;
1109 Visibility visibility = descriptor.getVisibility();
1110 boolean transformNeeded = !isLocal && !visibility.isPublicAPI()
1111 && !(definedInClass && Visibilities.PRIVATE.equals(visibility));
1112 if (transformNeeded) {
1113 if (type.getConstructor().getSupertypes().size() == 1) {
1114 assert type.getArguments().isEmpty() : "Object expression couldn't have any type parameters!";
1115 return type.getConstructor().getSupertypes().iterator().next();
1116 }
1117 else {
1118 trace.report(AMBIGUOUS_ANONYMOUS_TYPE_INFERRED.on(declaration, type.getConstructor().getSupertypes()));
1119 }
1120 }
1121 return type;
1122 }
1123
1124 @NotNull
1125 private JetType resolveInitializerType(
1126 @NotNull JetScope scope,
1127 @NotNull JetExpression initializer,
1128 @NotNull DataFlowInfo dataFlowInfo,
1129 @NotNull BindingTrace trace
1130 ) {
1131 return expressionTypingServices.safeGetType(scope, initializer, TypeUtils.NO_EXPECTED_TYPE, dataFlowInfo, trace);
1132 }
1133
1134 @Nullable
1135 private PropertySetterDescriptor resolvePropertySetterDescriptor(
1136 @NotNull JetScope scope,
1137 @NotNull JetProperty property,
1138 @NotNull PropertyDescriptor propertyDescriptor,
1139 BindingTrace trace
1140 ) {
1141 JetPropertyAccessor setter = property.getSetter();
1142 PropertySetterDescriptorImpl setterDescriptor = null;
1143 if (setter != null) {
1144 Annotations annotations =
1145 annotationResolver.resolveAnnotationsWithoutArguments(scope, setter.getModifierList(), trace);
1146 JetParameter parameter = setter.getParameter();
1147
1148 setterDescriptor = new PropertySetterDescriptorImpl(propertyDescriptor, annotations,
1149 resolveModalityFromModifiers(setter, propertyDescriptor.getModality()),
1150 resolveVisibilityFromModifiers(setter, propertyDescriptor.getVisibility()),
1151 setter.getBodyExpression() != null, false,
1152 CallableMemberDescriptor.Kind.DECLARATION, null);
1153 if (parameter != null) {
1154
1155 // This check is redundant: the parser does not allow a default value, but we'll keep it just in case
1156 JetExpression defaultValue = parameter.getDefaultValue();
1157 if (defaultValue != null) {
1158 trace.report(SETTER_PARAMETER_WITH_DEFAULT_VALUE.on(defaultValue));
1159 }
1160
1161 JetType type;
1162 JetTypeReference typeReference = parameter.getTypeReference();
1163 if (typeReference == null) {
1164 type = propertyDescriptor.getType(); // TODO : this maybe unknown at this point
1165 }
1166 else {
1167 type = typeResolver.resolveType(scope, typeReference, trace, true);
1168 JetType inType = propertyDescriptor.getType();
1169 if (inType != null) {
1170 if (!TypeUtils.equalTypes(type, inType)) {
1171 trace.report(WRONG_SETTER_PARAMETER_TYPE.on(typeReference, inType, type));
1172 }
1173 }
1174 else {
1175 // TODO : the same check may be needed later???
1176 }
1177 }
1178
1179 ValueParameterDescriptorImpl valueParameterDescriptor =
1180 resolveValueParameterDescriptor(scope, setterDescriptor, parameter, 0, type, trace);
1181 setterDescriptor.initialize(valueParameterDescriptor);
1182 }
1183 else {
1184 setterDescriptor.initializeDefault();
1185 }
1186
1187 trace.record(BindingContext.PROPERTY_ACCESSOR, setter, setterDescriptor);
1188 }
1189 else if (property.isVar()) {
1190 setterDescriptor = DescriptorFactory.createSetter(propertyDescriptor, property.getDelegateExpression() == null);
1191 }
1192
1193 if (!property.isVar()) {
1194 if (setter != null) {
1195 // trace.getErrorHandler().genericError(setter.asElement().getNode(), "A 'val'-property cannot have a setter");
1196 trace.report(VAL_WITH_SETTER.on(setter));
1197 }
1198 }
1199 return setterDescriptor;
1200 }
1201
1202 @Nullable
1203 private PropertyGetterDescriptorImpl resolvePropertyGetterDescriptor(
1204 @NotNull JetScope scope,
1205 @NotNull JetProperty property,
1206 @NotNull PropertyDescriptor propertyDescriptor,
1207 BindingTrace trace
1208 ) {
1209 PropertyGetterDescriptorImpl getterDescriptor;
1210 JetPropertyAccessor getter = property.getGetter();
1211 if (getter != null) {
1212 Annotations annotations =
1213 annotationResolver.resolveAnnotationsWithoutArguments(scope, getter.getModifierList(), trace);
1214
1215 JetType outType = propertyDescriptor.getType();
1216 JetType returnType = outType;
1217 JetTypeReference returnTypeReference = getter.getReturnTypeReference();
1218 if (returnTypeReference != null) {
1219 returnType = typeResolver.resolveType(scope, returnTypeReference, trace, true);
1220 if (outType != null && !TypeUtils.equalTypes(returnType, outType)) {
1221 trace.report(WRONG_GETTER_RETURN_TYPE.on(returnTypeReference, propertyDescriptor.getReturnType(), outType));
1222 }
1223 }
1224
1225 getterDescriptor = new PropertyGetterDescriptorImpl(propertyDescriptor, annotations,
1226 resolveModalityFromModifiers(getter, propertyDescriptor.getModality()),
1227 resolveVisibilityFromModifiers(getter, propertyDescriptor.getVisibility()),
1228 getter.getBodyExpression() != null, false,
1229 CallableMemberDescriptor.Kind.DECLARATION, null);
1230 getterDescriptor.initialize(returnType);
1231 trace.record(BindingContext.PROPERTY_ACCESSOR, getter, getterDescriptor);
1232 }
1233 else {
1234 getterDescriptor = DescriptorFactory.createGetter(propertyDescriptor, property.getDelegateExpression() == null);
1235 getterDescriptor.initialize(propertyDescriptor.getType());
1236 }
1237 return getterDescriptor;
1238 }
1239
1240 @NotNull
1241 private ConstructorDescriptorImpl createConstructorDescriptor(
1242 @NotNull JetScope scope,
1243 @NotNull ClassDescriptor classDescriptor,
1244 boolean isPrimary,
1245 @Nullable JetModifierList modifierList,
1246 @NotNull JetDeclaration declarationToTrace,
1247 List<TypeParameterDescriptor> typeParameters, @NotNull List<JetParameter> valueParameters, BindingTrace trace
1248 ) {
1249 ConstructorDescriptorImpl constructorDescriptor = ConstructorDescriptorImpl.create(
1250 classDescriptor,
1251 annotationResolver.resolveAnnotationsWithoutArguments(scope, modifierList, trace),
1252 isPrimary
1253 );
1254 trace.record(BindingContext.CONSTRUCTOR, declarationToTrace, constructorDescriptor);
1255 WritableScopeImpl parameterScope = new WritableScopeImpl(
1256 scope, constructorDescriptor, new TraceBasedRedeclarationHandler(trace), "Scope with value parameters of a constructor");
1257 parameterScope.changeLockLevel(WritableScope.LockLevel.BOTH);
1258 ConstructorDescriptorImpl constructor = constructorDescriptor.initialize(
1259 typeParameters,
1260 resolveValueParameters(
1261 constructorDescriptor,
1262 parameterScope,
1263 valueParameters, trace),
1264 resolveVisibilityFromModifiers(modifierList, getDefaultConstructorVisibility(classDescriptor)),
1265 DescriptorUtils.isConstructorOfStaticNestedClass(constructorDescriptor));
1266 if (isAnnotationClass(classDescriptor)) {
1267 CompileTimeConstantUtils.checkConstructorParametersType(valueParameters, trace);
1268 }
1269 return constructor;
1270 }
1271
1272 @Nullable
1273 public ConstructorDescriptorImpl resolvePrimaryConstructorDescriptor(
1274 @NotNull JetScope scope,
1275 @NotNull ClassDescriptor classDescriptor,
1276 @NotNull JetClass classElement,
1277 BindingTrace trace
1278 ) {
1279 if (classDescriptor.getKind() == ClassKind.ENUM_ENTRY) return null;
1280 return createConstructorDescriptor(
1281 scope,
1282 classDescriptor,
1283 true,
1284 classElement.getPrimaryConstructorModifierList(),
1285 classElement,
1286 classDescriptor.getTypeConstructor().getParameters(), classElement.getPrimaryConstructorParameters(), trace);
1287 }
1288
1289 @NotNull
1290 public PropertyDescriptor resolvePrimaryConstructorParameterToAProperty(
1291 @NotNull ClassDescriptor classDescriptor,
1292 @NotNull ValueParameterDescriptor valueParameter,
1293 @NotNull JetScope scope,
1294 @NotNull JetParameter parameter, BindingTrace trace
1295 ) {
1296 JetType type = resolveParameterType(scope, parameter, trace);
1297 Name name = parameter.getNameAsSafeName();
1298 boolean isMutable = parameter.isMutable();
1299 JetModifierList modifierList = parameter.getModifierList();
1300
1301 if (modifierList != null) {
1302 ASTNode abstractNode = modifierList.getModifierNode(JetTokens.ABSTRACT_KEYWORD);
1303 if (abstractNode != null) {
1304 trace.report(ABSTRACT_PROPERTY_IN_PRIMARY_CONSTRUCTOR_PARAMETERS.on(parameter));
1305 }
1306 }
1307
1308 PropertyDescriptorImpl propertyDescriptor = PropertyDescriptorImpl.create(
1309 classDescriptor,
1310 valueParameter.getAnnotations(),
1311 resolveModalityFromModifiers(parameter, Modality.FINAL),
1312 resolveVisibilityFromModifiers(parameter, Visibilities.INTERNAL),
1313 isMutable,
1314 name,
1315 CallableMemberDescriptor.Kind.DECLARATION
1316 );
1317 propertyDescriptor.setType(type, Collections.<TypeParameterDescriptor>emptyList(),
1318 getExpectedThisObjectIfNeeded(classDescriptor), NO_RECEIVER_PARAMETER);
1319
1320 PropertyGetterDescriptorImpl getter = DescriptorFactory.createDefaultGetter(propertyDescriptor);
1321 PropertySetterDescriptor setter =
1322 propertyDescriptor.isVar() ? DescriptorFactory.createDefaultSetter(propertyDescriptor) : null;
1323
1324 propertyDescriptor.initialize(getter, setter);
1325 getter.initialize(propertyDescriptor.getType());
1326
1327 trace.record(BindingContext.PRIMARY_CONSTRUCTOR_PARAMETER, parameter, propertyDescriptor);
1328 trace.record(BindingContext.VALUE_PARAMETER_AS_PROPERTY, valueParameter, propertyDescriptor);
1329 return propertyDescriptor;
1330 }
1331
1332 public static void checkBounds(@NotNull JetTypeReference typeReference, @NotNull JetType type, BindingTrace trace) {
1333 if (type.isError()) return;
1334
1335 JetTypeElement typeElement = typeReference.getTypeElement();
1336 if (typeElement == null) return;
1337
1338 List<TypeParameterDescriptor> parameters = type.getConstructor().getParameters();
1339 List<TypeProjection> arguments = type.getArguments();
1340 assert parameters.size() == arguments.size();
1341
1342 List<JetTypeReference> jetTypeArguments = typeElement.getTypeArgumentsAsTypes();
1343 assert jetTypeArguments.size() == arguments.size() : typeElement.getText();
1344
1345 TypeSubstitutor substitutor = TypeSubstitutor.create(type);
1346 for (int i = 0; i < jetTypeArguments.size(); i++) {
1347 JetTypeReference jetTypeArgument = jetTypeArguments.get(i);
1348
1349 if (jetTypeArgument == null) continue;
1350
1351 JetType typeArgument = arguments.get(i).getType();
1352 checkBounds(jetTypeArgument, typeArgument, trace);
1353
1354 TypeParameterDescriptor typeParameterDescriptor = parameters.get(i);
1355 checkBounds(jetTypeArgument, typeArgument, typeParameterDescriptor, substitutor, trace);
1356 }
1357 }
1358
1359 public static void checkBounds(
1360 @NotNull JetTypeReference jetTypeArgument,
1361 @NotNull JetType typeArgument,
1362 @NotNull TypeParameterDescriptor typeParameterDescriptor,
1363 @NotNull TypeSubstitutor substitutor, BindingTrace trace
1364 ) {
1365 for (JetType bound : typeParameterDescriptor.getUpperBounds()) {
1366 JetType substitutedBound = substitutor.safeSubstitute(bound, Variance.INVARIANT);
1367 if (!JetTypeChecker.INSTANCE.isSubtypeOf(typeArgument, substitutedBound)) {
1368 trace.report(UPPER_BOUND_VIOLATED.on(jetTypeArgument, substitutedBound, typeArgument));
1369 }
1370 }
1371 }
1372
1373 @NotNull
1374 public static SimpleFunctionDescriptor createEnumClassObjectValuesMethod(
1375 @NotNull ClassDescriptor classObject,
1376 @NotNull BindingTrace trace
1377 ) {
1378 final ClassDescriptor enumClassDescriptor = (ClassDescriptor) classObject.getContainingDeclaration();
1379 assert DescriptorUtils.isEnumClass(enumClassDescriptor) : "values should be created in enum class: " + enumClassDescriptor;
1380 return DescriptorFactory
1381 .createEnumClassObjectValuesMethod(classObject, DeferredType.create(NO_LOCKS, trace, new Function0<JetType>() {
1382 @Override
1383 public JetType invoke() {
1384 return KotlinBuiltIns.getInstance().getArrayType(enumClassDescriptor.getDefaultType());
1385 }
1386 }));
1387 }
1388
1389
1390 @NotNull
1391 public static SimpleFunctionDescriptor createEnumClassObjectValueOfMethod(
1392 @NotNull ClassDescriptor classObject,
1393 @NotNull BindingTrace trace
1394 ) {
1395 final ClassDescriptor enumClassDescriptor = (ClassDescriptor) classObject.getContainingDeclaration();
1396 assert DescriptorUtils.isEnumClass(enumClassDescriptor) : "valueOf should be created in enum class: " + enumClassDescriptor;
1397 return DescriptorFactory
1398 .createEnumClassObjectValueOfMethod(classObject, DeferredType.create(NO_LOCKS, trace, new Function0<JetType>() {
1399 @Override
1400 public JetType invoke() {
1401 return enumClassDescriptor.getDefaultType();
1402 }
1403 }));
1404 }
1405
1406 public static boolean checkHasOuterClassInstance(
1407 @NotNull JetScope scope,
1408 @NotNull BindingTrace trace,
1409 @NotNull PsiElement reportErrorsOn,
1410 @NotNull ClassDescriptor target
1411 ) {
1412 ClassDescriptor classDescriptor = getContainingClass(scope);
1413
1414 if (!isInsideOuterClassOrItsSubclass(classDescriptor, target)) {
1415 return true;
1416 }
1417
1418 while (classDescriptor != null) {
1419 if (isSubclass(classDescriptor, target)) {
1420 return true;
1421 }
1422
1423 if (isStaticNestedClass(classDescriptor)) {
1424 trace.report(INACCESSIBLE_OUTER_CLASS_EXPRESSION.on(reportErrorsOn, classDescriptor));
1425 return false;
1426 }
1427 classDescriptor = getParentOfType(classDescriptor, ClassDescriptor.class, true);
1428 }
1429 return true;
1430 }
1431
1432 public static void checkParameterHasNoValOrVar(
1433 @NotNull BindingTrace trace,
1434 @NotNull JetParameter parameter,
1435 @NotNull DiagnosticFactory1<PsiElement, JetKeywordToken> diagnosticFactory
1436 ) {
1437 ASTNode valOrVarNode = parameter.getValOrVarNode();
1438 if (valOrVarNode != null) {
1439 trace.report(diagnosticFactory.on(valOrVarNode.getPsi(), ((JetKeywordToken) valOrVarNode.getElementType())));
1440 }
1441 }
1442
1443 private static void checkConstructorParameterHasNoModifier(
1444 @NotNull BindingTrace trace,
1445 @NotNull JetParameter parameter
1446 ) {
1447 // If is not a property, then it must have no modifier
1448 if (parameter.getValOrVarNode() == null) {
1449 checkParameterHasNoModifier(trace, parameter);
1450 }
1451 }
1452
1453 public static void checkParameterHasNoModifier(
1454 @NotNull BindingTrace trace,
1455 @NotNull JetParameter parameter
1456 ) {
1457 JetModifierList modifiers = parameter.getModifierList();
1458 if (modifiers != null) {
1459 ASTNode node = modifiers.getNode().getFirstChildNode();
1460
1461 while (node != null) {
1462 IElementType elementType = node.getElementType();
1463
1464 if (elementType != JetTokens.VARARG_KEYWORD && elementType instanceof JetModifierKeywordToken) {
1465 trace.report(ILLEGAL_MODIFIER.on(node.getPsi(), (JetModifierKeywordToken) elementType));
1466 }
1467 node = node.getTreeNext();
1468 }
1469 }
1470 }
1471
1472 public static void resolvePackageHeader(
1473 @NotNull JetPackageDirective packageDirective,
1474 @NotNull ModuleDescriptor module,
1475 @NotNull BindingTrace trace
1476 ) {
1477 for (JetSimpleNameExpression nameExpression : packageDirective.getPackageNames()) {
1478 FqName fqName = packageDirective.getFqName(nameExpression);
1479
1480 PackageViewDescriptor packageView = module.getPackage(fqName);
1481 assert packageView != null : "package not found: " + fqName;
1482 trace.record(REFERENCE_TARGET, nameExpression, packageView);
1483
1484 PackageViewDescriptor parentPackageView = packageView.getContainingDeclaration();
1485 assert parentPackageView != null : "package has no parent: " + packageView;
1486 trace.record(RESOLUTION_SCOPE, nameExpression, parentPackageView.getMemberScope());
1487 }
1488 }
1489
1490 public static void registerFileInPackage(@NotNull BindingTrace trace, @NotNull JetFile file) {
1491 // Register files corresponding to this package
1492 // The trace currently does not support bi-di multimaps that would handle this task nicer
1493 FqName fqName = file.getPackageFqName();
1494 Collection<JetFile> files = trace.get(PACKAGE_TO_FILES, fqName);
1495 if (files == null) {
1496 files = Sets.newIdentityHashSet();
1497 }
1498 files.add(file);
1499 trace.record(BindingContext.PACKAGE_TO_FILES, fqName, files);
1500 }
1501 }