private static String getInlineName( @NotNull CodegenContext codegenContext, @NotNull DeclarationDescriptor currentDescriptor, @NotNull JetTypeMapper typeMapper, @NotNull JvmFileClassesProvider fileClassesProvider) { if (currentDescriptor instanceof PackageFragmentDescriptor) { PsiFile file = getContainingFile(codegenContext); Type implementationOwnerType; if (file == null) { implementationOwnerType = CodegenContextUtil.getImplementationOwnerClassType(codegenContext); } else { implementationOwnerType = FileClassesPackage.getFileClassType(fileClassesProvider, (JetFile) file); } if (implementationOwnerType == null) { DeclarationDescriptor contextDescriptor = codegenContext.getContextDescriptor(); //noinspection ConstantConditions throw new RuntimeException( "Couldn't find declaration for " + contextDescriptor.getContainingDeclaration().getName() + "." + contextDescriptor.getName() + "; context: " + codegenContext); } return implementationOwnerType.getInternalName(); } else if (currentDescriptor instanceof ClassifierDescriptor) { Type type = typeMapper.mapType((ClassifierDescriptor) currentDescriptor); return type.getInternalName(); } else if (currentDescriptor instanceof FunctionDescriptor) { ClassDescriptor descriptor = typeMapper .getBindingContext() .get(CodegenBinding.CLASS_FOR_CALLABLE, (FunctionDescriptor) currentDescriptor); if (descriptor != null) { Type type = typeMapper.mapType(descriptor); return type.getInternalName(); } } // TODO: add suffix for special case String suffix = currentDescriptor.getName().isSpecial() ? "" : currentDescriptor.getName().asString(); //noinspection ConstantConditions return getInlineName( codegenContext, currentDescriptor.getContainingDeclaration(), typeMapper, fileClassesProvider) + "$" + suffix; }
@Nullable public static ClassDescriptor getContainingClass(@NotNull DeclarationDescriptor descriptor) { DeclarationDescriptor containing = descriptor.getContainingDeclaration(); while (containing != null) { if (containing instanceof ClassDescriptor && !isCompanionObject(containing)) { return (ClassDescriptor) containing; } containing = containing.getContainingDeclaration(); } return null; }
public static boolean isAncestor( @Nullable DeclarationDescriptor ancestor, @NotNull DeclarationDescriptor declarationDescriptor, boolean strict) { if (ancestor == null) return false; DeclarationDescriptor descriptor = strict ? declarationDescriptor.getContainingDeclaration() : declarationDescriptor; while (descriptor != null) { if (ancestor == descriptor) return true; descriptor = descriptor.getContainingDeclaration(); } return false; }
@Nullable @SuppressWarnings("unchecked") public static <D extends DeclarationDescriptor> D getParentOfType( @Nullable DeclarationDescriptor descriptor, @NotNull Class<D> aClass, boolean strict) { if (descriptor == null) return null; if (strict) { descriptor = descriptor.getContainingDeclaration(); } while (descriptor != null) { if (aClass.isInstance(descriptor)) { return (D) descriptor; } descriptor = descriptor.getContainingDeclaration(); } return null; }
public static CodegenContext getContext(DeclarationDescriptor descriptor, GenerationState state) { if (descriptor instanceof PackageFragmentDescriptor) { return new PackageContext( (PackageFragmentDescriptor) descriptor, state.getRootContext(), null); } CodegenContext parent = getContext(descriptor.getContainingDeclaration(), state); if (descriptor instanceof ClassDescriptor) { OwnerKind kind = DescriptorUtils.isInterface(descriptor) ? OwnerKind.DEFAULT_IMPLS : OwnerKind.IMPLEMENTATION; return parent.intoClass((ClassDescriptor) descriptor, kind, state); } else if (descriptor instanceof ScriptDescriptor) { ClassDescriptor classDescriptorForScript = state.getBindingContext().get(CLASS_FOR_SCRIPT, (ScriptDescriptor) descriptor); assert classDescriptorForScript != null : "Can't find class for script: " + descriptor; List<ScriptDescriptor> earlierScripts = state.getEarlierScriptsForReplInterpreter(); return parent.intoScript( (ScriptDescriptor) descriptor, earlierScripts == null ? Collections.emptyList() : earlierScripts, classDescriptorForScript); } else if (descriptor instanceof FunctionDescriptor) { return parent.intoFunction((FunctionDescriptor) descriptor); } throw new IllegalStateException("Couldn't build context for " + descriptorName(descriptor)); }
@NotNull private static FqNameUnsafe getFqNameUnsafe(@NotNull DeclarationDescriptor descriptor) { DeclarationDescriptor containingDeclaration = descriptor.getContainingDeclaration(); assert containingDeclaration != null : "Not package/module descriptor doesn't have containing declaration: " + descriptor; return getFqName(containingDeclaration).child(descriptor.getName()); }
private static boolean isIllegalNestedClass(@NotNull DeclarationDescriptor descriptor) { if (!(descriptor instanceof ClassDescriptor)) return false; DeclarationDescriptor containingDeclaration = descriptor.getContainingDeclaration(); if (!(containingDeclaration instanceof ClassDescriptor)) return false; ClassDescriptor containingClass = (ClassDescriptor) containingDeclaration; return containingClass.isInner() || containingClass.getContainingDeclaration() instanceof FunctionDescriptor; }
@NotNull public static FqName getFqNameFromTopLevelClass(@NotNull DeclarationDescriptor descriptor) { DeclarationDescriptor containingDeclaration = descriptor.getContainingDeclaration(); Name name = descriptor.getName(); if (!(containingDeclaration instanceof ClassDescriptor)) { return FqName.topLevel(name); } return getFqNameFromTopLevelClass(containingDeclaration).child(name); }
/** Descriptor may be local itself or have a local ancestor */ public static boolean isLocal(@NotNull DeclarationDescriptor descriptor) { DeclarationDescriptor current = descriptor; while (current != null) { if (isAnonymousObject(current) || isDescriptorWithLocalVisibility(current)) { return true; } current = current.getContainingDeclaration(); } return false; }
@Nullable public static ModuleDescriptor getContainingModuleOrNull( @NotNull DeclarationDescriptor descriptor) { while (descriptor != null) { if (descriptor instanceof ModuleDescriptor) { return (ModuleDescriptor) descriptor; } if (descriptor instanceof PackageViewDescriptor) { return ((PackageViewDescriptor) descriptor).getModule(); } //noinspection ConstantConditions descriptor = descriptor.getContainingDeclaration(); } return null; }
@Override public MemberChooserObject getParentNodeDelegate() { DeclarationDescriptor parent = myDescriptor.getContainingDeclaration(); PsiElement declaration; if (myPsiElement instanceof JetDeclaration) { // kotlin declaration = PsiTreeUtil.getStubOrPsiParentOfType(myPsiElement, JetNamedDeclaration.class); } else { // java or bytecode declaration = ((PsiMember) myPsiElement).getContainingClass(); } assert parent != null : NO_PARENT_FOR + myDescriptor; assert declaration != null : NO_PARENT_FOR + myPsiElement; return new DescriptorClassMember(declaration, parent); }
@Nullable public TypeSubstitutor getOrCreateTypeSubstitutor() { if (!isInherited()) return null; if (typeSubstitutor == null) { if (samCallType == null) { typeSubstitutor = ChangeSignaturePackage.getFunctionSubstitutor(baseFunction, this); } else { DeclarationDescriptor currentBaseDescriptor = baseFunction.getCurrentFunctionDescriptor(); DeclarationDescriptor classDescriptor = currentBaseDescriptor != null ? currentBaseDescriptor.getContainingDeclaration() : null; if (!(classDescriptor instanceof ClassDescriptor)) return null; typeSubstitutor = ChangeSignaturePackage.getTypeSubstitutor( ((ClassDescriptor) classDescriptor).getDefaultType(), samCallType); } } return typeSubstitutor; }
/*descriptor is null for captured vars*/ public boolean shouldPutValue( @NotNull Type type, @Nullable StackValue stackValue, @Nullable ValueParameterDescriptor descriptor) { if (stackValue == null) { // default or vararg return true; } // remap only inline functions (and maybe non primitives) // TODO - clean asserion and remapping logic if (isPrimitive(type) != isPrimitive(stackValue.type)) { // don't remap boxing/unboxing primitives - lost identity and perfomance return true; } if (stackValue instanceof StackValue.Local) { return false; } StackValue field = stackValue; if (stackValue instanceof StackValue.FieldForSharedVar) { field = ((StackValue.FieldForSharedVar) stackValue).receiver; } // check that value corresponds to captured inlining parameter if (field instanceof StackValue.Field) { DeclarationDescriptor varDescriptor = ((StackValue.Field) field).descriptor; // check that variable is inline function parameter return !(varDescriptor instanceof ParameterDescriptor && InlineUtil.isInlineLambdaParameter((ParameterDescriptor) varDescriptor) && InlineUtil.isInline(varDescriptor.getContainingDeclaration())); } return true; }
public boolean isMemberOfAny(@NotNull DeclarationDescriptor descriptor) { return descriptor.getContainingDeclaration() == getAny(); }
/** * @return true if descriptor is a class inside another class and does not have access to the * outer class */ public static boolean isStaticNestedClass(@NotNull DeclarationDescriptor descriptor) { DeclarationDescriptor containing = descriptor.getContainingDeclaration(); return descriptor instanceof ClassDescriptor && containing instanceof ClassDescriptor && !((ClassDescriptor) descriptor).isInner(); }
private void checkSupertypeList( @NotNull ClassDescriptor supertypeOwner, @NotNull Map<JetTypeReference, JetType> supertypes, @NotNull JetClassOrObject jetClass) { Set<TypeConstructor> allowedFinalSupertypes = getAllowedFinalSupertypes(supertypeOwner, jetClass); Set<TypeConstructor> typeConstructors = Sets.newHashSet(); boolean classAppeared = false; for (Map.Entry<JetTypeReference, JetType> entry : supertypes.entrySet()) { JetTypeReference typeReference = entry.getKey(); JetType supertype = entry.getValue(); boolean addSupertype = true; ClassDescriptor classDescriptor = TypeUtils.getClassDescriptor(supertype); if (classDescriptor != null) { if (ErrorUtils.isError(classDescriptor)) continue; if (classDescriptor.getKind() != ClassKind.INTERFACE) { if (supertypeOwner.getKind() == ClassKind.ENUM_CLASS) { trace.report(CLASS_IN_SUPERTYPE_FOR_ENUM.on(typeReference)); addSupertype = false; } else if (supertypeOwner.getKind() == ClassKind.INTERFACE && !classAppeared && !TypesPackage.isDynamic(supertype) /* avoid duplicate diagnostics */) { trace.report(TRAIT_WITH_SUPERCLASS.on(typeReference)); addSupertype = false; } if (classAppeared) { trace.report(MANY_CLASSES_IN_SUPERTYPE_LIST.on(typeReference)); } else { classAppeared = true; } } } else { trace.report(SUPERTYPE_NOT_A_CLASS_OR_TRAIT.on(typeReference)); } TypeConstructor constructor = supertype.getConstructor(); if (addSupertype && !typeConstructors.add(constructor)) { trace.report(SUPERTYPE_APPEARS_TWICE.on(typeReference)); } if (DescriptorUtils.isSingleton(classDescriptor)) { trace.report(SINGLETON_IN_SUPERTYPE.on(typeReference)); } else if (constructor.isFinal() && !allowedFinalSupertypes.contains(constructor)) { if (classDescriptor.getModality() == Modality.SEALED) { DeclarationDescriptor containingDescriptor = supertypeOwner.getContainingDeclaration(); while (containingDescriptor != null && containingDescriptor != classDescriptor) { containingDescriptor = containingDescriptor.getContainingDeclaration(); } if (containingDescriptor == null) { trace.report(SEALED_SUPERTYPE.on(typeReference)); } else { trace.report(SEALED_SUPERTYPE_IN_LOCAL_CLASS.on(typeReference)); } } else { trace.report(FINAL_SUPERTYPE.on(typeReference)); } } } }
public static boolean isTopLevelDeclaration(@Nullable DeclarationDescriptor descriptor) { return descriptor != null && descriptor.getContainingDeclaration() instanceof PackageFragmentDescriptor; }