예제 #1
0
  public void resolvePropertyAccessors(
      @NotNull BodiesResolveContext c,
      @NotNull JetProperty property,
      @NotNull PropertyDescriptor propertyDescriptor) {
    ObservableBindingTrace fieldAccessTrackingTrace = createFieldTrackingTrace(propertyDescriptor);

    JetPropertyAccessor getter = property.getGetter();
    PropertyGetterDescriptor getterDescriptor = propertyDescriptor.getGetter();
    if (getter != null && getterDescriptor != null) {
      LexicalScope accessorScope = makeScopeForPropertyAccessor(c, getter, propertyDescriptor);
      ForceResolveUtil.forceResolveAllContents(getterDescriptor.getAnnotations());
      resolveFunctionBody(
          c.getOuterDataFlowInfo(),
          fieldAccessTrackingTrace,
          getter,
          getterDescriptor,
          accessorScope);
    }

    JetPropertyAccessor setter = property.getSetter();
    PropertySetterDescriptor setterDescriptor = propertyDescriptor.getSetter();
    if (setter != null && setterDescriptor != null) {
      LexicalScope accessorScope = makeScopeForPropertyAccessor(c, setter, propertyDescriptor);
      ForceResolveUtil.forceResolveAllContents(setterDescriptor.getAnnotations());
      resolveFunctionBody(
          c.getOuterDataFlowInfo(),
          fieldAccessTrackingTrace,
          setter,
          setterDescriptor,
          accessorScope);
    }
  }
예제 #2
0
  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);
  }
예제 #3
0
  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));
      }
    }
  }
예제 #4
0
  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));
      }
    }
  }