@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
  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;
  }