private void checkAccessors( @NotNull JetProperty property, @NotNull PropertyDescriptor propertyDescriptor) { for (JetPropertyAccessor accessor : property.getAccessors()) { PropertyAccessorDescriptor propertyAccessorDescriptor = accessor.isGetter() ? propertyDescriptor.getGetter() : propertyDescriptor.getSetter(); assert propertyAccessorDescriptor != null : "No property accessor descriptor for " + property.getText(); modifiersChecker.checkModifiersForDeclaration(accessor, propertyAccessorDescriptor); modifiersChecker.reportIllegalModalityModifiers(accessor); } JetPropertyAccessor getter = property.getGetter(); PropertyGetterDescriptor getterDescriptor = propertyDescriptor.getGetter(); JetModifierList getterModifierList = getter != null ? getter.getModifierList() : null; if (getterModifierList != null && getterDescriptor != null) { Map<JetModifierKeywordToken, ASTNode> nodes = ModifiersChecker.getNodesCorrespondingToModifiers( getterModifierList, Sets.newHashSet( JetTokens.PUBLIC_KEYWORD, JetTokens.PROTECTED_KEYWORD, JetTokens.PRIVATE_KEYWORD, JetTokens.INTERNAL_KEYWORD)); if (getterDescriptor.getVisibility() != propertyDescriptor.getVisibility()) { for (ASTNode node : nodes.values()) { trace.report(Errors.GETTER_VISIBILITY_DIFFERS_FROM_PROPERTY_VISIBILITY.on(node.getPsi())); } } else { for (ASTNode node : nodes.values()) { trace.report(Errors.REDUNDANT_MODIFIER_IN_GETTER.on(node.getPsi())); } } } }
public void resolvePropertyDelegate( @NotNull DataFlowInfo outerDataFlowInfo, @NotNull JetProperty jetProperty, @NotNull PropertyDescriptor propertyDescriptor, @NotNull JetExpression delegateExpression, @NotNull LexicalScope parentScopeForAccessor, @NotNull LexicalScope propertyScope) { JetPropertyAccessor getter = jetProperty.getGetter(); if (getter != null && getter.hasBody()) { trace.report(ACCESSOR_FOR_DELEGATED_PROPERTY.on(getter)); } JetPropertyAccessor setter = jetProperty.getSetter(); if (setter != null && setter.hasBody()) { trace.report(ACCESSOR_FOR_DELEGATED_PROPERTY.on(setter)); } LexicalScope propertyDeclarationInnerScope = JetScopeUtils.getPropertyDeclarationInnerScopeForInitializer( propertyDescriptor, propertyScope, propertyDescriptor.getTypeParameters(), null, trace); LexicalScope accessorScope = JetScopeUtils.makeScopeForPropertyAccessor( propertyDescriptor, parentScopeForAccessor, trace); JetType delegateType = delegatedPropertyResolver.resolveDelegateExpression( delegateExpression, jetProperty, propertyDescriptor, propertyDeclarationInnerScope, accessorScope, trace, outerDataFlowInfo); delegatedPropertyResolver.resolveDelegatedPropertyGetMethod( propertyDescriptor, delegateExpression, delegateType, trace, accessorScope); if (jetProperty.isVar()) { delegatedPropertyResolver.resolveDelegatedPropertySetMethod( propertyDescriptor, delegateExpression, delegateType, trace, accessorScope); } delegatedPropertyResolver.resolveDelegatedPropertyPDMethod( propertyDescriptor, delegateExpression, delegateType, trace, accessorScope); }
private LexicalScope makeScopeForPropertyAccessor( @NotNull BodiesResolveContext c, @NotNull JetPropertyAccessor accessor, @NotNull PropertyDescriptor descriptor) { LexicalScope accessorDeclaringScope = c.getDeclaringScope(accessor); assert accessorDeclaringScope != null : "Scope for accessor " + accessor.getText() + " should exists"; return JetScopeUtils.makeScopeForPropertyAccessor(descriptor, accessorDeclaringScope, trace); }
private void checkPropertyAbstractness( @NotNull JetProperty property, @NotNull PropertyDescriptor propertyDescriptor, @NotNull ClassDescriptor classDescriptor) { JetPropertyAccessor getter = property.getGetter(); JetPropertyAccessor setter = property.getSetter(); JetModifierList modifierList = property.getModifierList(); ASTNode abstractNode = modifierList != null ? modifierList.getModifierNode(JetTokens.ABSTRACT_KEYWORD) : null; if (abstractNode != null) { // has abstract modifier if (!classCanHaveAbstractMembers(classDescriptor)) { String name = property.getName(); trace.report( ABSTRACT_PROPERTY_IN_NON_ABSTRACT_CLASS.on( property, name != null ? name : "", classDescriptor)); return; } if (classDescriptor.getKind() == ClassKind.INTERFACE) { trace.report(ABSTRACT_MODIFIER_IN_TRAIT.on(property)); } } if (propertyDescriptor.getModality() == Modality.ABSTRACT) { JetExpression initializer = property.getInitializer(); if (initializer != null) { trace.report(ABSTRACT_PROPERTY_WITH_INITIALIZER.on(initializer)); } JetPropertyDelegate delegate = property.getDelegate(); if (delegate != null) { trace.report(ABSTRACT_DELEGATED_PROPERTY.on(delegate)); } if (getter != null && getter.hasBody()) { trace.report(ABSTRACT_PROPERTY_WITH_GETTER.on(getter)); } if (setter != null && setter.hasBody()) { trace.report(ABSTRACT_PROPERTY_WITH_SETTER.on(setter)); } } }
private void checkPropertyInitializer( @NotNull JetProperty property, @NotNull PropertyDescriptor propertyDescriptor) { JetPropertyAccessor getter = property.getGetter(); JetPropertyAccessor setter = property.getSetter(); boolean hasAccessorImplementation = (getter != null && getter.hasBody()) || (setter != null && setter.hasBody()); if (propertyDescriptor.getModality() == Modality.ABSTRACT) { if (!property.hasDelegateExpressionOrInitializer() && property.getTypeReference() == null) { trace.report(PROPERTY_WITH_NO_TYPE_NO_INITIALIZER.on(property)); } return; } DeclarationDescriptor containingDeclaration = propertyDescriptor.getContainingDeclaration(); boolean inTrait = containingDeclaration instanceof ClassDescriptor && ((ClassDescriptor) containingDeclaration).getKind() == ClassKind.INTERFACE; JetExpression initializer = property.getInitializer(); JetPropertyDelegate delegate = property.getDelegate(); boolean backingFieldRequired = Boolean.TRUE.equals( trace .getBindingContext() .get(BindingContext.BACKING_FIELD_REQUIRED, propertyDescriptor)); if (inTrait && backingFieldRequired && hasAccessorImplementation) { trace.report(BACKING_FIELD_IN_TRAIT.on(property)); } if (initializer == null && delegate == null) { boolean error = false; if (backingFieldRequired && !inTrait && Boolean.TRUE.equals( trace.getBindingContext().get(BindingContext.IS_UNINITIALIZED, propertyDescriptor))) { if (!(containingDeclaration instanceof ClassDescriptor) || hasAccessorImplementation) { error = true; trace.report(MUST_BE_INITIALIZED.on(property)); } else { error = true; trace.report(MUST_BE_INITIALIZED_OR_BE_ABSTRACT.on(property)); } } if (!error && property.getTypeReference() == null) { trace.report(PROPERTY_WITH_NO_TYPE_NO_INITIALIZER.on(property)); } if (inTrait && property.hasModifier(JetTokens.FINAL_KEYWORD) && backingFieldRequired) { trace.report(FINAL_PROPERTY_IN_TRAIT.on(property)); } return; } if (inTrait) { if (delegate != null) { trace.report(DELEGATED_PROPERTY_IN_TRAIT.on(delegate)); } else { trace.report(PROPERTY_INITIALIZER_IN_TRAIT.on(initializer)); } } else if (delegate == null) { if (!backingFieldRequired) { trace.report(PROPERTY_INITIALIZER_NO_BACKING_FIELD.on(initializer)); } else if (property.getReceiverTypeReference() != null) { trace.report(EXTENSION_PROPERTY_WITH_BACKING_FIELD.on(initializer)); } } }