예제 #1
0
  @NotNull
  public static Collection<ClassDescriptor> getClassOrObjectDescriptorsByFqName(
      @NotNull ResolveSession resolveSession,
      @NotNull FqName fqName,
      boolean includeObjectDeclarations) {
    if (fqName.isRoot()) {
      return Collections.emptyList();
    }

    Collection<ClassDescriptor> classDescriptors = Lists.newArrayList();

    FqName packageFqName = fqName.parent();
    while (true) {
      NamespaceDescriptor packageDescriptor =
          resolveSession.getPackageDescriptorByFqName(packageFqName);
      if (packageDescriptor != null) {
        FqName classInPackagePath = new FqName(QualifiedNamesUtil.tail(packageFqName, fqName));
        Collection<ClassDescriptor> descriptors =
            getClassOrObjectDescriptorsByFqName(
                packageDescriptor, classInPackagePath, includeObjectDeclarations);
        classDescriptors.addAll(descriptors);
      }

      if (packageFqName.isRoot()) {
        break;
      } else {
        packageFqName = packageFqName.parent();
      }
    }

    return classDescriptors;
  }
예제 #2
0
  public static boolean isImported(@NotNull ImportPath alreadyImported, @NotNull FqName fqName) {
    if (alreadyImported.isAllUnder() && !fqName.isRoot()) {
      return alreadyImported.fqnPart().equals(fqName.parent());
    }

    return alreadyImported.fqnPart().equals(fqName);
  }
예제 #3
0
  @NotNull
  private static Set<DeclarationDescriptor> getTopLevelDescriptorsByFqName(
      @NotNull KotlinCodeAnalyzer resolveSession, @NotNull FqName fqName) {
    FqName parentFqName = fqName.parent();

    Set<DeclarationDescriptor> descriptors = new HashSet<DeclarationDescriptor>();

    LazyPackageDescriptor parentFragment = resolveSession.getPackageFragment(parentFqName);
    if (parentFragment != null) {
      // Filter out extension properties
      descriptors.addAll(
          KotlinPackage.filter(
              parentFragment.getMemberScope().getProperties(fqName.shortName()),
              new Function1<VariableDescriptor, Boolean>() {
                @Override
                public Boolean invoke(VariableDescriptor descriptor) {
                  return descriptor.getReceiverParameter() == null;
                }
              }));
    }

    ContainerUtil.addIfNotNull(descriptors, resolveSession.getPackageFragment(fqName));

    descriptors.addAll(resolveSession.getTopLevelClassDescriptors(fqName));
    return descriptors;
  }
 @NotNull
 public static Collection<FqName> getTopLevelFunctionFqNames(
     @NotNull Project project, @NotNull GlobalSearchScope scope, boolean shouldBeExtension) {
   Collection<FqName> result = Sets.newHashSet();
   Collection<PsiClass> packageClasses =
       getClassesByAnnotation(KotlinPackage.class.getSimpleName(), project, scope);
   for (PsiClass psiClass : packageClasses) {
     String qualifiedName = psiClass.getQualifiedName();
     if (qualifiedName == null) {
       continue;
     }
     FqName packageFqName = new FqName(qualifiedName).parent();
     PackageData data = getPackageData(psiClass);
     if (data == null) {
       continue;
     }
     NameResolver nameResolver = data.getNameResolver();
     for (ProtoBuf.Callable callable : data.getPackageProto().getMemberList()) {
       if (callable.hasReceiverType() == shouldBeExtension) {
         Name name = nameResolver.getName(callable.getName());
         result.add(packageFqName.child(name));
       }
     }
   }
   return result;
 }
 @NotNull
 @Override
 public Collection<DeclarationDescriptor> getAllDescriptors() {
   List<DeclarationDescriptor> result = Lists.newArrayList();
   for (FqName subFqName : module.getPackageFragmentProvider().getSubPackagesOf(fqName)) {
     ContainerUtil.addIfNotNull(result, getPackage(subFqName.shortName()));
   }
   return result;
 }
예제 #6
0
  @NotNull
  public static FqName withoutFirstSegment(@NotNull FqName fqName) {
    if (fqName.isRoot() || fqName.parent().isRoot()) {
      return FqName.ROOT;
    }

    String fqNameStr = fqName.getFqName();
    return new FqName(fqNameStr.substring(fqNameStr.indexOf('.'), fqNameStr.length()));
  }
예제 #7
0
  /**
   * Get tail part of the full fqn by subtracting head part.
   *
   * @param headFQN
   * @param fullFQN
   * @return tail fqn. If first part is not a begging of the full fqn, fullFQN will be returned.
   */
  @NotNull
  public static String tail(@NotNull FqName headFQN, @NotNull FqName fullFQN) {
    if (!isSubpackageOf(fullFQN, headFQN) || headFQN.isRoot()) {
      return fullFQN.getFqName();
    }

    return fullFQN.equals(headFQN)
        ? ""
        : fullFQN.getFqName().substring(headFQN.getFqName().length() + 1); // (headFQN + '.').length
  }
예제 #8
0
 @Override
 public void serialize(@NotNull PsiJetParameterStub stub, @NotNull StubOutputStream dataStream)
     throws IOException {
   dataStream.writeName(stub.getName());
   dataStream.writeBoolean(stub.isMutable());
   dataStream.writeBoolean(stub.isVarArg());
   dataStream.writeName(stub.getTypeText());
   dataStream.writeName(stub.getDefaultValueText());
   FqName name = stub.getFqName();
   dataStream.writeName(name != null ? name.asString() : null);
 }
예제 #9
0
  @Nullable
  public AnnotationDescriptor resolveAnnotation(
      @NotNull JavaAnnotation javaAnnotation, @NotNull PostponedTasks postponedTasks) {
    final AnnotationDescriptor annotation = new AnnotationDescriptor();
    FqName fqName = javaAnnotation.getFqName();
    if (fqName == null) {
      return null;
    }

    // Don't process internal jet annotations and jetbrains NotNull annotations
    if (fqName.asString().startsWith("jet.runtime.typeinfo.")
        || fqName.equals(JETBRAINS_NOT_NULL_ANNOTATION)
        || fqName.equals(JvmAnnotationNames.KOTLIN_CLASS)
        || fqName.equals(JvmAnnotationNames.KOTLIN_PACKAGE)) {
      return null;
    }

    AnnotationDescriptor mappedClassDescriptor =
        JavaToKotlinClassMap.getInstance().mapToAnnotationClass(fqName);
    if (mappedClassDescriptor != null) {
      return mappedClassDescriptor;
    }

    final ClassDescriptor annotationClass =
        classResolver.resolveClass(fqName, INCLUDE_KOTLIN_SOURCES, postponedTasks);
    if (annotationClass == null) {
      return null;
    }

    postponedTasks.addTask(
        new Runnable() {
          @Override
          public void run() {
            annotation.setAnnotationType(annotationClass.getDefaultType());
          }
        });

    for (JavaAnnotationArgument argument : javaAnnotation.getArguments()) {
      CompileTimeConstant value =
          argumentResolver.resolveAnnotationArgument(fqName, argument, postponedTasks);
      if (value == null) continue;

      Name name = argument.getName();
      ValueParameterDescriptor descriptor =
          DescriptorResolverUtils.getAnnotationParameterByName(
              name == null ? DEFAULT_ANNOTATION_MEMBER_NAME : name, annotationClass);
      if (descriptor != null) {
        annotation.setValueArgument(descriptor, value);
      }
    }

    return annotation;
  }
예제 #10
0
  public Collection<ClassDescriptor> getJetClassesDescriptors(
      @NotNull Condition<String> acceptedShortNameCondition, @NotNull KotlinCodeAnalyzer analyzer) {
    Collection<ClassDescriptor> classDescriptors = new ArrayList<ClassDescriptor>();

    for (String fqName : JetFullClassNameIndex.getInstance().getAllKeys(project)) {
      FqName classFQName = new FqName(fqName);
      if (acceptedShortNameCondition.value(classFQName.shortName().getName())) {
        classDescriptors.addAll(
            ResolveSessionUtils.getClassDescriptorsByFqName(analyzer, classFQName));
      }
    }

    return classDescriptors;
  }
예제 #11
0
  private void initPrimitives() {
    KotlinBuiltIns builtIns = KotlinBuiltIns.getInstance();
    for (JvmPrimitiveType jvmPrimitiveType : JvmPrimitiveType.values()) {
      PrimitiveType primitiveType = jvmPrimitiveType.getPrimitiveType();
      String name = jvmPrimitiveType.getName();
      FqName wrapperFqName = jvmPrimitiveType.getWrapperFqName();

      register(wrapperFqName, builtIns.getPrimitiveClassDescriptor(primitiveType));
      primitiveTypesMap.put(name, builtIns.getPrimitiveJetType(primitiveType));
      primitiveTypesMap.put("[" + name, builtIns.getPrimitiveArrayJetType(primitiveType));
      primitiveTypesMap.put(
          wrapperFqName.asString(), builtIns.getNullablePrimitiveJetType(primitiveType));
    }
    primitiveTypesMap.put("void", KotlinBuiltIns.getInstance().getUnitType());
  }
예제 #12
0
  @Override
  public void indexProperty(PsiJetPropertyStub stub, IndexSink sink) {
    String propertyName = stub.getName();
    if (propertyName != null) {
      if (stub.isTopLevel()) {
        FqName topFQName = stub.getTopFQName();
        if (topFQName != null) {
          sink.occurrence(
              JetTopLevelPropertiesFqnNameIndex.getInstance().getKey(), topFQName.getFqName());
        }
      }

      sink.occurrence(JetShortPropertiesNameIndex.getInstance().getKey(), propertyName);
    }
  }
예제 #13
0
  @Override
  public void indexFile(PsiJetFileStub stub, IndexSink sink) {
    String packageName = stub.getPackageName();
    FqName fqName = new FqName(packageName == null ? "" : packageName);

    sink.occurrence(JetPackageDeclarationIndex.getInstance().getKey(), fqName.getFqName());

    while (true) {
      sink.occurrence(JetAllPackagesIndex.getInstance().getKey(), fqName.getFqName());
      if (fqName.isRoot()) {
        return;
      }
      fqName = fqName.parent();
    }
  }
예제 #14
0
 // TODO: includeRuntime should be not a flag but a path to runtime
 public static void writeToJar(
     ClassFileFactory factory,
     final OutputStream fos,
     @Nullable FqName mainClass,
     boolean includeRuntime) {
   try {
     Manifest manifest = new Manifest();
     final Attributes mainAttributes = manifest.getMainAttributes();
     mainAttributes.putValue("Manifest-Version", "1.0");
     mainAttributes.putValue("Created-By", "JetBrains Kotlin");
     if (mainClass != null) {
       mainAttributes.putValue("Main-Class", mainClass.getFqName());
     }
     JarOutputStream stream = new JarOutputStream(fos, manifest);
     for (String file : factory.files()) {
       stream.putNextEntry(new JarEntry(file));
       stream.write(factory.asBytes(file));
     }
     if (includeRuntime) {
       writeRuntimeToJar(stream);
     }
     stream.finish();
   } catch (IOException e) {
     throw new CompileEnvironmentException("Failed to generate jar file", e);
   }
 }
예제 #15
0
  /** Check that import is useless. */
  private static boolean isImportedByDefault(
      @NotNull ImportPath importPath, @Nullable String aliasName, @NotNull FqName filePackageFqn) {
    if (importPath.fqnPart().isRoot()) {
      return true;
    }

    if (aliasName != null) {
      return false;
    }

    // Single element import without .* and alias is useless
    if (!importPath.isAllUnder() && QualifiedNamesUtil.isOneSegmentFQN(importPath.fqnPart())) {
      return true;
    }

    // There's no need to import a declaration from the package of current file
    if (!importPath.isAllUnder() && filePackageFqn.equals(importPath.fqnPart().parent())) {
      return true;
    }

    if (isImportedWithKotlinDefault(importPath)) return true;

    if (isImportedWithJavaDefault(importPath)) return true;

    return false;
  }
예제 #16
0
  public static boolean isSubpackageOf(
      @NotNull final FqName subpackageName, @NotNull FqName packageName) {
    if (subpackageName.equals(packageName)) {
      return true;
    }

    if (packageName.isRoot()) {
      return true;
    }

    String subpackageNameStr = subpackageName.getFqName();
    String packageNameStr = packageName.getFqName();

    return (subpackageNameStr.startsWith(packageNameStr)
        && subpackageNameStr.charAt(packageNameStr.length()) == '.');
  }
예제 #17
0
 @NotNull
 @Override
 public Collection<Name> getClassNames(@NotNull FqName packageName) {
   return packageName.equals(KotlinBuiltIns.BUILT_INS_PACKAGE_FQ_NAME)
       ? classNames.invoke()
       : Collections.<Name>emptyList();
 }
예제 #18
0
 @Override
 public boolean isEqual(FqName val1, FqName val2) {
   if (val1 == null) {
     return val2 == null;
   }
   return val1.equals(val1);
 }
예제 #19
0
 @Nullable
 public AnnotationDescriptor mapToAnnotationClass(@NotNull FqName fqName) {
   ClassDescriptor classDescriptor = classDescriptorMap.get(fqName);
   if (classDescriptor != null && fqName.equals(JAVA_LANG_DEPRECATED)) {
     return getAnnotationDescriptorForJavaLangDeprecated(classDescriptor);
   }
   return null;
 }
예제 #20
0
 @NotNull
 @Override
 public Collection<FqName> getSubPackagesOf(@NotNull FqName fqName) {
   if (fqName.isRoot()) {
     return Collections.singleton(KotlinBuiltIns.BUILT_INS_PACKAGE_FQ_NAME);
   }
   return Collections.emptyList();
 }
예제 #21
0
  @Override
  public void indexObject(PsiJetObjectStub stub, IndexSink sink) {
    String name = stub.getName();
    assert name != null;

    sink.occurrence(JetShortClassNameIndex.getInstance().getKey(), name);

    if (stub.isTopLevel()) {
      sink.occurrence(JetTopLevelShortObjectNameIndex.getInstance().getKey(), name);
    }

    FqName fqName = stub.getFQName();
    if (fqName != null) {
      sink.occurrence(JetFullClassNameIndex.getInstance().getKey(), fqName.getFqName());
    }

    recordClassOrObjectByPackage(stub, sink);
  }
예제 #22
0
  @Nullable
  public static ClassDescriptor getKotlinBuiltinClassDescriptor(@NotNull FqName qualifiedName) {
    if (!qualifiedName.firstSegmentIs(KotlinBuiltIns.BUILT_INS_PACKAGE_NAME)) return null;

    List<Name> segments = qualifiedName.pathSegments();
    if (segments.size() < 2) return null;

    JetScope scope = KotlinBuiltIns.getInstance().getBuiltInsPackageScope();
    for (int i = 1, size = segments.size(); i < size; i++) {
      ClassifierDescriptor classifier = scope.getClassifier(segments.get(i));
      if (classifier == null) return null;
      assert classifier instanceof ClassDescriptor
          : "Unexpected classifier in built-ins: " + classifier;
      scope = ((ClassDescriptor) classifier).getUnsubstitutedInnerClassesScope();
    }

    return (ClassDescriptor) scope.getContainingDeclaration();
  }
예제 #23
0
  public static void addImportDirectiveOrChangeToFqName(
      @NotNull FqName importFqn,
      @NotNull JetFile file,
      int refOffset,
      @NotNull PsiElement targetElement) {
    PsiReference reference = file.findReferenceAt(refOffset);
    if (reference instanceof JetPsiReference) {
      PsiElement target = reference.resolve();
      if (target != null) {
        boolean same = file.getManager().areElementsEquivalent(target, targetElement);

        if (!same) {
          same =
              target instanceof PsiClass
                  && importFqn.getFqName().equals(((PsiClass) target).getQualifiedName());
        }

        if (!same) {
          if (target instanceof PsiMethod) {
            PsiMethod method = (PsiMethod) target;
            same =
                (method.isConstructor()
                    && file.getManager()
                        .areElementsEquivalent(method.getContainingClass(), targetElement));
          }
        }

        if (!same) {
          if (target instanceof JetObjectDeclarationName) {
            same = file.getManager().areElementsEquivalent(target.getParent(), targetElement);
          }
        }

        if (!same) {
          Document document = PsiDocumentManager.getInstance(file.getProject()).getDocument(file);
          TextRange refRange = reference.getElement().getTextRange();
          document.replaceString(
              refRange.getStartOffset(), refRange.getEndOffset(), importFqn.getFqName());
        }
        return;
      }
    }
    addImportDirective(new ImportPath(importFqn, false), null, file);
  }
예제 #24
0
 @Override
 public ClassDescriptor getObjectDescriptor(@NotNull Name name) {
   ClassDescriptor classDescriptor =
       getResolver()
           .resolveClass(packageFQN.child(name), DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN);
   if (classDescriptor != null && classDescriptor.getKind().isObject()) {
     return classDescriptor;
   }
   return null;
 }
예제 #25
0
 @NotNull
 @Override
 public List<PackageFragmentDescriptor> getPackageFragments(@NotNull FqName fqName) {
   if (fqName.isRoot()) {
     return Collections.singletonList(rootPackage);
   } else if (KotlinBuiltIns.BUILT_INS_PACKAGE_FQ_NAME.equals(fqName)) {
     return Collections.<PackageFragmentDescriptor>singletonList(BuiltinsPackageFragment.this);
   }
   return Collections.emptyList();
 }
  @Nullable
  @Override
  public ClassDescriptor getClass(@NotNull JavaClass javaClass) {
    FqName fqName = javaClass.getFqName();
    if (fqName != null && KotlinBuiltIns.BUILT_INS_PACKAGE_FQ_NAME.equals(fqName.parent())) {
      if (javaClass.findAnnotation(ASSERT_INVISIBLE_IN_RESOLVER_ANNOTATION) != null) {
        if (ApplicationManager.getApplication().isInternal()) {
          LOG.error(
              "Classpath is configured incorrectly:"
                  + " class "
                  + fqName
                  + " from runtime must not be loaded by compiler");
        }
        return null;
      }
    }

    return trace.get(CLASS, ((JavaClassImpl) javaClass).getPsi());
  }
예제 #27
0
  @Override
  public void visitClassType(String name, boolean nullable, boolean forceReal) {
    FqName ourName =
        new FqName(
            name.replace('/', '.').replace('$', '.') // TODO: not sure
            );

    this.classDescriptor = null;
    if (!forceReal) {
      classDescriptor =
          javaSemanticServices
              .getTypeTransformer()
              .getKotlinAnalog(ourName, JavaTypeTransformer.TypeUsage.MEMBER_SIGNATURE_INVARIANT);
    }

    if (classDescriptor == null) {
      // TODO: this is the worst code in Kotlin project
      Matcher matcher = Pattern.compile("jet\\.Function(\\d+)").matcher(ourName.getFqName());
      if (matcher.matches()) {
        classDescriptor = JetStandardClasses.getFunction(Integer.parseInt(matcher.group(1)));
      }
    }

    if (classDescriptor == null) {
      Matcher matcher = Pattern.compile("jet\\.Tuple(\\d+)").matcher(ourName.getFqName());
      if (matcher.matches()) {
        classDescriptor = JetStandardClasses.getTuple(Integer.parseInt(matcher.group(1)));
      }
    }

    if (this.classDescriptor == null) {
      this.classDescriptor =
          javaDescriptorResolver.resolveClass(ourName, DescriptorSearchRule.INCLUDE_KOTLIN);
    }

    if (this.classDescriptor == null) {
      // TODO: report in to trace
      this.errorType = ErrorUtils.createErrorType("class not found by name: " + ourName);
    }
    this.nullable = nullable;
    this.typeArguments = new ArrayList<TypeProjection>();
  }
예제 #28
0
  @Nullable
  private static FqName getFQName(@Nullable JetExpression expression) {
    if (expression == null) {
      return null;
    }

    if (expression instanceof JetDotQualifiedExpression) {
      JetDotQualifiedExpression dotQualifiedExpression = (JetDotQualifiedExpression) expression;
      FqName parentFqn = getFQName(dotQualifiedExpression.getReceiverExpression());
      Name child = getName(dotQualifiedExpression.getSelectorExpression());

      return parentFqn != null && child != null ? parentFqn.child(child) : null;
    } else if (expression instanceof JetSimpleNameExpression) {
      JetSimpleNameExpression simpleNameExpression = (JetSimpleNameExpression) expression;
      return FqName.topLevel(simpleNameExpression.getReferencedNameAsName());
    } else {
      throw new IllegalArgumentException(
          "Can't construct fqn for: " + expression.getClass().toString());
    }
  }
  public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;

    PackageViewDescriptorImpl that = (PackageViewDescriptorImpl) o;

    if (!fqName.equals(that.fqName)) return false;
    if (!module.equals(that.module)) return false;

    return true;
  }
예제 #30
0
  @Nullable
  public static FqName getFQName(@NotNull JetNamedDeclaration namedDeclaration) {
    Name name = namedDeclaration.getNameAsName();
    if (name == null) {
      return null;
    }

    PsiElement parent = namedDeclaration.getParent();
    if (parent instanceof JetClassBody) {
      // One nesting to JetClassBody doesn't affect to qualified name
      parent = parent.getParent();
    }

    FqName firstPart = null;
    if (parent instanceof JetFile) {
      firstPart = getFQName((JetFile) parent);
    } else if (parent instanceof JetNamedFunction || parent instanceof JetClass) {
      firstPart = getFQName((JetNamedDeclaration) parent);
    } else if (namedDeclaration instanceof JetParameter) {
      JetClass constructorClass = getClassIfParameterIsProperty((JetParameter) namedDeclaration);
      if (constructorClass != null) {
        firstPart = getFQName(constructorClass);
      }
    } else if (parent instanceof JetObjectDeclaration) {
      if (parent.getParent() instanceof JetClassObject) {
        JetClassOrObject classOrObject =
            PsiTreeUtil.getParentOfType(parent, JetClassOrObject.class);
        if (classOrObject != null) {
          firstPart = getFQName(classOrObject);
        }
      } else {
        firstPart = getFQName((JetNamedDeclaration) parent);
      }
    }

    if (firstPart == null) {
      return null;
    }

    return firstPart.child(name);
  }