@Nullable
 public static List<ValueParameterDescriptor> getSubstitutedValueParameters(
     FunctionDescriptor substitutedDescriptor,
     @NotNull FunctionDescriptor functionDescriptor,
     @NotNull TypeSubstitutor substitutor) {
   List<ValueParameterDescriptor> result = new ArrayList<ValueParameterDescriptor>();
   List<ValueParameterDescriptor> unsubstitutedValueParameters =
       functionDescriptor.getValueParameters();
   for (int i = 0, unsubstitutedValueParametersSize = unsubstitutedValueParameters.size();
       i < unsubstitutedValueParametersSize;
       i++) {
     ValueParameterDescriptor unsubstitutedValueParameter = unsubstitutedValueParameters.get(i);
     // TODO : Lazy?
     JetType substitutedType =
         substitutor.substitute(unsubstitutedValueParameter.getType(), Variance.IN_VARIANCE);
     JetType varargElementType = unsubstitutedValueParameter.getVarargElementType();
     JetType substituteVarargElementType =
         varargElementType == null
             ? null
             : substitutor.substitute(varargElementType, Variance.IN_VARIANCE);
     if (substitutedType == null) return null;
     result.add(
         new ValueParameterDescriptorImpl(
             substitutedDescriptor,
             unsubstitutedValueParameter,
             unsubstitutedValueParameter.getAnnotations(),
             unsubstitutedValueParameter.isVar(),
             substitutedType,
             substituteVarargElementType));
   }
   return result;
 }
Example #2
0
  private TypeSubstitutor createTypeSubstitutorWithDefaultForUnknownTypeParameter(
      @Nullable final TypeProjection defaultTypeProjection) {
    return TypeSubstitutor.create(
        new TypeSubstitution() {
          @Override
          public TypeProjection get(TypeConstructor key) {
            DeclarationDescriptor declarationDescriptor = key.getDeclarationDescriptor();
            if (declarationDescriptor instanceof TypeParameterDescriptor) {
              TypeParameterDescriptor descriptor = (TypeParameterDescriptor) declarationDescriptor;

              JetType value = ConstraintsUtil.getValue(getTypeConstraints(descriptor));
              if (value != null
                  && !TypeUtils.dependsOnTypeParameterConstructors(
                      value, Collections.singleton(DONT_CARE.getConstructor()))) {
                return new TypeProjection(value);
              }
              if (typeParameterConstraints.containsKey(descriptor)) {
                return defaultTypeProjection;
              }
            }
            return null;
          }

          @Override
          public boolean isEmpty() {
            return false;
          }

          @Override
          public String toString() {
            return typeParameterConstraints.toString();
          }
        });
  }
 @Nullable
 public static FunctionDescriptor substituteFunctionDescriptor(
     @NotNull List<JetType> typeArguments, @NotNull FunctionDescriptor functionDescriptor) {
   Map<TypeConstructor, TypeProjection> substitutionContext =
       createSubstitutionContext(functionDescriptor, typeArguments);
   return functionDescriptor.substitute(TypeSubstitutor.create(substitutionContext));
 }
Example #4
0
 @Nullable
 public static KotlinType createSubstitutedSupertype(
     @NotNull KotlinType subType,
     @NotNull KotlinType superType,
     @NotNull TypeSubstitutor substitutor) {
   KotlinType substitutedType = substitutor.substitute(superType, Variance.INVARIANT);
   if (substitutedType != null) {
     return makeNullableIfNeeded(substitutedType, subType.isMarkedNullable());
   }
   return null;
 }
Example #5
0
 @NotNull
 public static List<KotlinType> getImmediateSupertypes(@NotNull KotlinType type) {
   TypeSubstitutor substitutor = TypeSubstitutor.create(type);
   Collection<KotlinType> originalSupertypes = type.getConstructor().getSupertypes();
   List<KotlinType> result = new ArrayList<KotlinType>(originalSupertypes.size());
   for (KotlinType supertype : originalSupertypes) {
     KotlinType substitutedType = createSubstitutedSupertype(type, supertype, substitutor);
     if (substitutedType != null) {
       result.add(substitutedType);
     }
   }
   return result;
 }
  @NotNull
  private static FunctionDescriptor substituteSuperFunction(
      @NotNull Map<ClassDescriptor, JetType> superclassToSupertype,
      @NotNull FunctionDescriptor superFun) {
    DeclarationDescriptor superFunContainer = superFun.getContainingDeclaration();
    assert superFunContainer instanceof ClassDescriptor : superFunContainer;

    JetType supertype = superclassToSupertype.get(superFunContainer);
    assert supertype != null : "Couldn't find super type for super function: " + superFun;
    TypeSubstitutor supertypeSubstitutor = TypeSubstitutor.create(supertype);

    FunctionDescriptor substitutedSuperFun = superFun.substitute(supertypeSubstitutor);
    assert substitutedSuperFun != null;
    return substitutedSuperFun;
  }
Example #7
0
  @NotNull
  public static KotlinType substituteProjectionsForParameters(
      @NotNull ClassDescriptor clazz, @NotNull List<TypeProjection> projections) {
    List<TypeParameterDescriptor> clazzTypeParameters = clazz.getTypeConstructor().getParameters();
    if (clazzTypeParameters.size() != projections.size()) {
      throw new IllegalArgumentException(
          "type parameter counts do not match: " + clazz + ", " + projections);
    }

    Map<TypeConstructor, TypeProjection> substitutions =
        org.jetbrains.kotlin.utils.CollectionsKt.newHashMapWithExpectedSize(
            clazzTypeParameters.size());

    for (int i = 0; i < clazzTypeParameters.size(); ++i) {
      TypeConstructor typeConstructor = clazzTypeParameters.get(i).getTypeConstructor();
      substitutions.put(typeConstructor, projections.get(i));
    }

    return TypeSubstitutor.create(substitutions)
        .substitute(clazz.getDefaultType(), Variance.INVARIANT);
  }
public class FunctionDescriptorUtil {
  private static final TypeSubstitutor MAKE_TYPE_PARAMETERS_FRESH =
      TypeSubstitutor.create(
          new TypeSubstitution() {

            @Override
            public TypeProjection get(TypeConstructor key) {
              return null;
            }

            @Override
            public boolean isEmpty() {
              return false;
            }

            @Override
            public String toString() {
              return "FunctionDescriptorUtil.MAKE_TYPE_PARAMETERS_FRESH";
            }
          });

  public static Map<TypeConstructor, TypeProjection> createSubstitutionContext(
      @NotNull FunctionDescriptor functionDescriptor, List<JetType> typeArguments) {
    if (functionDescriptor.getTypeParameters().isEmpty()) return Collections.emptyMap();

    Map<TypeConstructor, TypeProjection> result = new HashMap<TypeConstructor, TypeProjection>();

    int typeArgumentsSize = typeArguments.size();
    List<TypeParameterDescriptor> typeParameters = functionDescriptor.getTypeParameters();
    assert typeArgumentsSize == typeParameters.size();
    for (int i = 0; i < typeArgumentsSize; i++) {
      TypeParameterDescriptor typeParameterDescriptor = typeParameters.get(i);
      JetType typeArgument = typeArguments.get(i);
      result.put(typeParameterDescriptor.getTypeConstructor(), new TypeProjection(typeArgument));
    }
    return result;
  }

  @Nullable
  public static List<ValueParameterDescriptor> getSubstitutedValueParameters(
      FunctionDescriptor substitutedDescriptor,
      @NotNull FunctionDescriptor functionDescriptor,
      @NotNull TypeSubstitutor substitutor) {
    List<ValueParameterDescriptor> result = new ArrayList<ValueParameterDescriptor>();
    List<ValueParameterDescriptor> unsubstitutedValueParameters =
        functionDescriptor.getValueParameters();
    for (int i = 0, unsubstitutedValueParametersSize = unsubstitutedValueParameters.size();
        i < unsubstitutedValueParametersSize;
        i++) {
      ValueParameterDescriptor unsubstitutedValueParameter = unsubstitutedValueParameters.get(i);
      // TODO : Lazy?
      JetType substitutedType =
          substitutor.substitute(unsubstitutedValueParameter.getType(), Variance.IN_VARIANCE);
      JetType varargElementType = unsubstitutedValueParameter.getVarargElementType();
      JetType substituteVarargElementType =
          varargElementType == null
              ? null
              : substitutor.substitute(varargElementType, Variance.IN_VARIANCE);
      if (substitutedType == null) return null;
      result.add(
          new ValueParameterDescriptorImpl(
              substitutedDescriptor,
              unsubstitutedValueParameter,
              unsubstitutedValueParameter.getAnnotations(),
              unsubstitutedValueParameter.isVar(),
              substitutedType,
              substituteVarargElementType));
    }
    return result;
  }

  @Nullable
  public static JetType getSubstitutedReturnType(
      @NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
    return substitutor.substitute(functionDescriptor.getReturnType(), Variance.OUT_VARIANCE);
  }

  @Nullable
  public static FunctionDescriptor substituteFunctionDescriptor(
      @NotNull List<JetType> typeArguments, @NotNull FunctionDescriptor functionDescriptor) {
    Map<TypeConstructor, TypeProjection> substitutionContext =
        createSubstitutionContext(functionDescriptor, typeArguments);
    return functionDescriptor.substitute(TypeSubstitutor.create(substitutionContext));
  }

  @NotNull
  public static JetScope getFunctionInnerScope(
      @NotNull JetScope outerScope,
      @NotNull FunctionDescriptor descriptor,
      @NotNull BindingTrace trace) {
    WritableScope parameterScope =
        new WritableScopeImpl(
            outerScope,
            descriptor,
            new TraceBasedRedeclarationHandler(trace),
            "Function inner scope");
    ReceiverParameterDescriptor receiver = descriptor.getReceiverParameter();
    if (receiver != null) {
      parameterScope.setImplicitReceiver(receiver);
    }
    for (TypeParameterDescriptor typeParameter : descriptor.getTypeParameters()) {
      parameterScope.addTypeParameterDescriptor(typeParameter);
    }
    for (ValueParameterDescriptor valueParameterDescriptor : descriptor.getValueParameters()) {
      parameterScope.addVariableDescriptor(valueParameterDescriptor);
    }
    parameterScope.addLabeledDeclaration(descriptor);
    parameterScope.changeLockLevel(WritableScope.LockLevel.READING);
    return parameterScope;
  }

  public static void initializeFromFunctionType(
      @NotNull FunctionDescriptorImpl functionDescriptor,
      @NotNull JetType functionType,
      @Nullable ReceiverParameterDescriptor expectedThisObject,
      @NotNull Modality modality,
      @NotNull Visibility visibility) {

    assert KotlinBuiltIns.getInstance().isFunctionOrExtensionFunctionType(functionType);
    functionDescriptor.initialize(
        KotlinBuiltIns.getInstance().getReceiverType(functionType),
        expectedThisObject,
        Collections.<TypeParameterDescriptorImpl>emptyList(),
        KotlinBuiltIns.getInstance().getValueParameters(functionDescriptor, functionType),
        KotlinBuiltIns.getInstance().getReturnTypeFromFunctionType(functionType),
        modality,
        visibility);
  }

  public static <D extends CallableDescriptor> D alphaConvertTypeParameters(D candidate) {
    return (D) candidate.substitute(MAKE_TYPE_PARAMETERS_FRESH);
  }

  public static FunctionDescriptor getInvokeFunction(@NotNull JetType functionType) {
    assert KotlinBuiltIns.getInstance().isFunctionOrExtensionFunctionType(functionType);

    ClassifierDescriptor classDescriptorForFunction =
        functionType.getConstructor().getDeclarationDescriptor();
    assert classDescriptorForFunction instanceof ClassDescriptor;
    Collection<FunctionDescriptor> invokeFunctions =
        ((ClassDescriptor) classDescriptorForFunction)
            .getMemberScope(functionType.getArguments())
            .getFunctions(Name.identifier("invoke"));
    assert invokeFunctions.size() == 1;
    return invokeFunctions.iterator().next();
  }
}
 @Nullable
 public static JetType getSubstitutedReturnType(
     @NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
   return substitutor.substitute(functionDescriptor.getReturnType(), Variance.OUT_VARIANCE);
 }