예제 #1
0
  @Override
  protected void generateBody() {
    List<KtObjectDeclaration> companions = new ArrayList<KtObjectDeclaration>();
    if (kind != OwnerKind.DEFAULT_IMPLS) {
      // generate nested classes first and only then generate class body. It necessary to access to
      // nested CodegenContexts
      for (KtDeclaration declaration : myClass.getDeclarations()) {
        if (shouldProcessFirst(declaration)) {
          // Generate companions after class body generation (need to record all synthetic
          // accessors)
          if (declaration instanceof KtObjectDeclaration
              && ((KtObjectDeclaration) declaration).isCompanion()) {
            companions.add((KtObjectDeclaration) declaration);
            CodegenUtilKt.populateCompanionBackingFieldNamesToOuterContextIfNeeded(
                (KtObjectDeclaration) declaration, context, state);
          } else {
            generateDeclaration(declaration);
          }
        }
      }
    }

    for (KtDeclaration declaration : myClass.getDeclarations()) {
      if (!shouldProcessFirst(declaration)) {
        generateDeclaration(declaration);
      }
    }

    generatePrimaryConstructorProperties();
    generateConstructors();
    generateDefaultImplsIfNeeded();

    for (KtObjectDeclaration companion : companions) {
      generateDeclaration(companion);
    }

    if (!DescriptorUtils.isInterface(descriptor)) {
      for (DeclarationDescriptor memberDescriptor :
          DescriptorUtils.getAllDescriptors(descriptor.getDefaultType().getMemberScope())) {
        if (memberDescriptor instanceof CallableMemberDescriptor) {
          CallableMemberDescriptor member = (CallableMemberDescriptor) memberDescriptor;
          if (!member.getKind().isReal() && ImplKt.findInterfaceImplementation(member) == null) {
            if (member instanceof FunctionDescriptor) {
              functionCodegen.generateBridges((FunctionDescriptor) member);
            } else if (member instanceof PropertyDescriptor) {
              PropertyGetterDescriptor getter = ((PropertyDescriptor) member).getGetter();
              if (getter != null) {
                functionCodegen.generateBridges(getter);
              }
              PropertySetterDescriptor setter = ((PropertyDescriptor) member).getSetter();
              if (setter != null) {
                functionCodegen.generateBridges(setter);
              }
            }
          }
        }
      }
    }
  }
예제 #2
0
  private static void generateTypeCheckBarrierIfNeeded(
      @NotNull InstructionAdapter iv,
      @NotNull FunctionDescriptor descriptor,
      @NotNull Type returnType,
      @Nullable final Type delegateParameterType) {
    BuiltinMethodsWithSpecialGenericSignature.DefaultValue defaultValue =
        BuiltinMethodsWithSpecialGenericSignature.getDefaultValueForOverriddenBuiltinFunction(
            descriptor);
    if (defaultValue == null) return;

    assert descriptor.getValueParameters().size() == 1
        : "Should be descriptor with one value parameter, but found: " + descriptor;

    boolean isCheckForAny =
        delegateParameterType == null || OBJECT_TYPE.equals(delegateParameterType);

    final KotlinType kotlinType = descriptor.getValueParameters().get(0).getType();

    if (isCheckForAny && TypeUtils.isNullableType(kotlinType)) return;

    iv.load(1, OBJECT_TYPE);

    Label afterBarrier = new Label();

    if (isCheckForAny) {
      assert !TypeUtils.isNullableType(kotlinType)
          : "Only bridges for not-nullable types are necessary";
      iv.ifnonnull(afterBarrier);
    } else {
      CodegenUtilKt.generateIsCheck(iv, kotlinType, boxType(delegateParameterType));
      iv.ifne(afterBarrier);
    }

    StackValue.constant(defaultValue.getValue(), returnType).put(returnType, iv);
    iv.areturn(returnType);

    iv.visitLabel(afterBarrier);
  }