Big refactoring. Migrating to package views and fragments.

This commit is contained in:
Evgeny Gerashchenko
2013-10-11 21:43:40 +04:00
parent 369824cd2e
commit 7abe6a5b4a
141 changed files with 1728 additions and 1465 deletions
@@ -269,7 +269,7 @@ public class AsmUtil {
return ACC_PROTECTED;
}
}
if (containingDeclaration instanceof NamespaceDescriptor) {
if (containingDeclaration instanceof PackageFragmentDescriptor) {
return ACC_PUBLIC;
}
return null;
@@ -25,7 +25,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.codegen.binding.CalculatedClosure;
import org.jetbrains.jet.codegen.context.CodegenContext;
import org.jetbrains.jet.codegen.context.NamespaceContext;
import org.jetbrains.jet.codegen.context.PackageContext;
import org.jetbrains.jet.codegen.signature.BothSignatureWriter;
import org.jetbrains.jet.codegen.signature.JvmMethodParameterKind;
import org.jetbrains.jet.codegen.signature.JvmMethodSignature;
@@ -194,7 +194,7 @@ public class CodegenUtil {
return !isFakeOverride && !isDelegate &&
(((context.hasThisDescriptor() && containingDeclaration == context.getThisDescriptor()) ||
(context.getParentContext() instanceof NamespaceContext && context.getParentContext().getContextDescriptor() == containingDeclaration))
(context.getParentContext() instanceof PackageContext && context.getParentContext().getContextDescriptor() == containingDeclaration))
&& context.getContextKind() != OwnerKind.TRAIT_IMPL);
}
@@ -1782,7 +1782,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
DeclarationDescriptor containingDeclaration = propertyDescriptor.getContainingDeclaration();
boolean isBackingFieldInAnotherClass = AsmUtil.isPropertyWithBackingFieldInOuterClass(propertyDescriptor);
boolean isStatic = containingDeclaration instanceof NamespaceDescriptor;
boolean isStatic = containingDeclaration instanceof PackageFragmentDescriptor;
boolean isSuper = superExpression != null;
boolean isInsideClass = isCallInsideSameClassAsDeclared(propertyDescriptor, context);
boolean isInsideModule = isCallInsideSameModuleAsDeclared(propertyDescriptor, context);
@@ -32,7 +32,7 @@ import org.jetbrains.asm4.util.TraceMethodVisitor;
import org.jetbrains.jet.codegen.binding.CodegenBinding;
import org.jetbrains.jet.codegen.context.CodegenContext;
import org.jetbrains.jet.codegen.context.MethodContext;
import org.jetbrains.jet.codegen.context.NamespaceFacadeContext;
import org.jetbrains.jet.codegen.context.PackageFacadeContext;
import org.jetbrains.jet.codegen.signature.JvmMethodParameterKind;
import org.jetbrains.jet.codegen.signature.JvmMethodParameterSignature;
import org.jetbrains.jet.codegen.signature.JvmMethodSignature;
@@ -113,8 +113,8 @@ public class FunctionCodegen extends ParentCodegenAwareImpl {
jvmSignature.getGenericsSignature(),
null);
if (owner instanceof NamespaceFacadeContext) {
Type ownerType = ((NamespaceFacadeContext) owner).getDelegateToClassType();
if (owner instanceof PackageFacadeContext) {
Type ownerType = ((PackageFacadeContext) owner).getDelegateToClassType();
v.getSerializationBindings().put(IMPL_CLASS_NAME_FOR_CALLABLE, functionDescriptor, shortNameByAsmType(ownerType));
}
else {
@@ -274,8 +274,8 @@ public class FunctionCodegen extends ParentCodegenAwareImpl {
Label methodBegin = new Label();
mv.visitLabel(methodBegin);
if (context.getParentContext() instanceof NamespaceFacadeContext) {
generateStaticDelegateMethodBody(mv, signature.getAsmMethod(), (NamespaceFacadeContext) context.getParentContext());
if (context.getParentContext() instanceof PackageFacadeContext) {
generateStaticDelegateMethodBody(mv, signature.getAsmMethod(), (PackageFacadeContext) context.getParentContext());
}
else {
FrameMap frameMap = strategy.getFrameMap(typeMapper, context);
@@ -411,7 +411,7 @@ public class FunctionCodegen extends ParentCodegenAwareImpl {
private static void generateStaticDelegateMethodBody(
@NotNull MethodVisitor mv,
@NotNull Method asmMethod,
@NotNull NamespaceFacadeContext context
@NotNull PackageFacadeContext context
) {
InstructionAdapter iv = new InstructionAdapter(mv);
Type[] argTypes = asmMethod.getArgumentTypes();
@@ -585,7 +585,7 @@ public class FunctionCodegen extends ParentCodegenAwareImpl {
int flags = ACC_PUBLIC | ACC_SYNTHETIC; // TODO.
Type ownerType;
if (contextClass instanceof NamespaceDescriptor) {
if (contextClass instanceof PackageFragmentDescriptor) {
ownerType = state.getTypeMapper().getOwner(functionDescriptor, kind, true);
}
else if (contextClass instanceof ClassDescriptor) {
@@ -143,7 +143,7 @@ public class FunctionTypesUtil {
JetScope builtInsScope = KotlinBuiltIns.getInstance().getBuiltInsScope();
MutableClassDescriptor functionImpl = new MutableClassDescriptor(
builtInsScope.getContainingDeclaration(),
KotlinBuiltIns.getInstance().getBuiltInsPackageFragment(),
builtInsScope,
ClassKind.CLASS,
false,
@@ -234,7 +234,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
boolean isObjectLiteral = DescriptorUtils.isAnonymousObject(descriptor);
boolean isLocalOrAnonymousClass = isObjectLiteral ||
!(parentDescriptor instanceof NamespaceDescriptor || parentDescriptor instanceof ClassDescriptor);
!(parentDescriptor instanceof PackageFragmentDescriptor || parentDescriptor instanceof ClassDescriptor);
// Do not emit enclosing method in "light-classes mode" since currently we genenerate local light classes as if they're top level
if (isLocalOrAnonymousClass && getState().getClassBuilderMode() != ClassBuilderMode.LIGHT_CLASSES) {
String outerClassName = getOuterClassName(descriptor, typeMapper);
@@ -16,11 +16,13 @@
package org.jetbrains.jet.codegen;
import com.google.common.collect.Sets;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.progress.ProcessCanceledException;
import com.intellij.openapi.util.io.FileUtil;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.PsiFile;
import com.intellij.util.ArrayUtil;
import com.intellij.util.PathUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -33,7 +35,7 @@ import org.jetbrains.jet.descriptors.serialization.BitEncoding;
import org.jetbrains.jet.descriptors.serialization.DescriptorSerializer;
import org.jetbrains.jet.descriptors.serialization.PackageData;
import org.jetbrains.jet.descriptors.serialization.ProtoBuf;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.descriptors.*;
import org.jetbrains.jet.lang.diagnostics.DiagnosticUtils;
import org.jetbrains.jet.lang.psi.*;
import org.jetbrains.jet.lang.resolve.BindingContext;
@@ -43,9 +45,7 @@ import org.jetbrains.jet.lang.resolve.java.JvmClassName;
import org.jetbrains.jet.lang.resolve.name.FqName;
import org.jetbrains.jet.lang.resolve.name.Name;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.*;
import static org.jetbrains.asm4.Opcodes.*;
import static org.jetbrains.jet.codegen.AsmUtil.asmDescByFqNameWithoutInnerClasses;
@@ -54,7 +54,6 @@ import static org.jetbrains.jet.descriptors.serialization.NameSerializationUtil.
import static org.jetbrains.jet.lang.resolve.java.PackageClassUtils.getPackageClassFqName;
public class NamespaceCodegen extends MemberCodegen {
@NotNull
private final ClassBuilderOnDemand v;
@NotNull
@@ -62,7 +61,7 @@ public class NamespaceCodegen extends MemberCodegen {
@NotNull
private final Collection<JetFile> files;
private final NamespaceDescriptor descriptor;
private final Set<PackageFragmentDescriptor> packageFragments;
public NamespaceCodegen(
@NotNull ClassBuilderOnDemand v,
@@ -77,8 +76,10 @@ public class NamespaceCodegen extends MemberCodegen {
name = fqName;
this.files = namespaceFiles;
descriptor = state.getBindingContext().get(BindingContext.FQNAME_TO_NAMESPACE_DESCRIPTOR, name);
assert descriptor != null : "No namespace found for FQ name " + name;
packageFragments = Sets.newHashSet();
for (JetFile file : namespaceFiles) {
packageFragments.add(getPackageFragment(file));
}
final PsiFile sourceFile = namespaceFiles.size() == 1 ? namespaceFiles.iterator().next().getContainingFile() : null;
@@ -89,9 +90,8 @@ public class NamespaceCodegen extends MemberCodegen {
ACC_PUBLIC | ACC_FINAL,
JvmClassName.byFqNameWithoutInnerClasses(getPackageClassFqName(fqName)).getInternalName(),
null,
//"jet/lang/Namespace",
"java/lang/Object",
new String[0]
ArrayUtil.EMPTY_STRING_ARRAY
);
//We don't generate any source information for namespace with multiple files
if (sourceFile != null) {
@@ -147,7 +147,7 @@ public class NamespaceCodegen extends MemberCodegen {
}
DescriptorSerializer serializer = new DescriptorSerializer(new JavaSerializerExtension(bindings));
ProtoBuf.Package packageProto = serializer.packageProto(descriptor).build();
ProtoBuf.Package packageProto = serializer.packageProto(packageFragments).build();
if (packageProto.getMemberCount() == 0) return;
@@ -167,7 +167,7 @@ public class NamespaceCodegen extends MemberCodegen {
@Nullable
private ClassBuilder generate(@NotNull JetFile file) {
boolean generateSrcClass = false;
FieldOwnerContext packageFragmentContext = CodegenContext.STATIC.intoNamespace(descriptor);
FieldOwnerContext packagePartContext = CodegenContext.STATIC.intoPackagePart(getPackageFragment(file));
for (JetDeclaration declaration : file.getDeclarations()) {
if (declaration instanceof JetProperty || declaration instanceof JetNamedFunction) {
@@ -179,18 +179,18 @@ public class NamespaceCodegen extends MemberCodegen {
}
}
else if (declaration instanceof JetScript) {
ScriptCodegen.createScriptCodegen((JetScript) declaration, state, packageFragmentContext).generate();
ScriptCodegen.createScriptCodegen((JetScript) declaration, state, packagePartContext).generate();
}
}
if (!generateSrcClass) return null;
Type packageFragmentType = getNamespacePartType(getPackageClassFqName(name), file.getVirtualFile());
ClassBuilder builder = state.getFactory().forPackageFragment(packageFragmentType, file);
Type packagePartType = getNamespacePartType(getPackageClassFqName(name), file.getVirtualFile());
ClassBuilder builder = state.getFactory().forPackageFragment(packagePartType, file);
new NamespacePartCodegen(builder, file, packageFragmentType, packageFragmentContext, state).generate();
new NamespacePartCodegen(builder, file, packagePartType, packagePartContext, state).generate();
FieldOwnerContext namespaceFacade = CodegenContext.STATIC.intoNamespaceFacade(packageFragmentType, descriptor);
FieldOwnerContext namespaceFacade = CodegenContext.STATIC.intoPackageFacade(packagePartType, getPackageFragment(file));
for (JetDeclaration declaration : file.getDeclarations()) {
if (declaration instanceof JetNamedFunction || declaration instanceof JetProperty) {
@@ -201,8 +201,15 @@ public class NamespaceCodegen extends MemberCodegen {
return builder;
}
@NotNull
private PackageFragmentDescriptor getPackageFragment(@NotNull JetFile file) {
PackageFragmentDescriptor packageFragment = bindingContext.get(BindingContext.FILE_TO_PACKAGE_FRAGMENT, file);
assert packageFragment != null : "package fragment is null for " + file;
return packageFragment;
}
public void generateClassOrObject(@NotNull JetClassOrObject classOrObject) {
CodegenContext context = CodegenContext.STATIC.intoNamespace(descriptor);
CodegenContext context = CodegenContext.STATIC.intoPackagePart(getPackageFragment((JetFile) classOrObject.getContainingFile()));
genClassOrObject(context, classOrObject);
}
@@ -17,6 +17,7 @@
package org.jetbrains.jet.codegen;
import com.google.common.collect.Lists;
import com.intellij.util.ArrayUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.asm4.AnnotationVisitor;
import org.jetbrains.asm4.MethodVisitor;
@@ -42,7 +43,7 @@ public class NamespacePartCodegen extends MemberCodegen {
private final ClassBuilder v;
private final NamespaceDescriptor descriptor;
private final PackageFragmentDescriptor descriptor;
private final JetFile jetFile;
@@ -62,7 +63,7 @@ public class NamespacePartCodegen extends MemberCodegen {
this.jetFile = jetFile;
this.namespacePartName = namespacePartName;
this.context = context;
descriptor = state.getBindingContext().get(BindingContext.FILE_TO_NAMESPACE, jetFile);
descriptor = state.getBindingContext().get(BindingContext.FILE_TO_PACKAGE_FRAGMENT, jetFile);
assert descriptor != null : "No namespace found for jetFile " + jetFile + " declared package: " + jetFile.getPackageName();
}
@@ -71,9 +72,8 @@ public class NamespacePartCodegen extends MemberCodegen {
ACC_PUBLIC | ACC_FINAL,
namespacePartName.getInternalName(),
null,
//"jet/lang/Namespace",
"java/lang/Object",
new String[0]
ArrayUtil.EMPTY_STRING_ARRAY
);
v.visitSource(jetFile.getName(), null);
@@ -28,7 +28,7 @@ import org.jetbrains.asm4.commons.InstructionAdapter;
import org.jetbrains.asm4.commons.Method;
import org.jetbrains.jet.codegen.context.CodegenContext;
import org.jetbrains.jet.codegen.context.FieldOwnerContext;
import org.jetbrains.jet.codegen.context.NamespaceFacadeContext;
import org.jetbrains.jet.codegen.context.PackageFacadeContext;
import org.jetbrains.jet.codegen.signature.JvmMethodSignature;
import org.jetbrains.jet.codegen.state.GenerationState;
import org.jetbrains.jet.codegen.state.GenerationStateAware;
@@ -92,8 +92,8 @@ public class PropertyCodegen extends GenerationStateAware {
: "Generating property with a wrong kind (" + kind + "): " + propertyDescriptor;
if (context instanceof NamespaceFacadeContext) {
Type ownerType = ((NamespaceFacadeContext) context).getDelegateToClassType();
if (context instanceof PackageFacadeContext) {
Type ownerType = ((PackageFacadeContext) context).getDelegateToClassType();
v.getSerializationBindings().put(IMPL_CLASS_NAME_FOR_CALLABLE, propertyDescriptor, shortNameByAsmType(ownerType));
}
else if (!generateBackingField(p, propertyDescriptor)) {
@@ -379,8 +379,8 @@ class CodegenAnnotatingVisitor extends JetVisitorVoid {
if (containingDeclaration instanceof ClassDescriptor) {
return peek + '$' + name;
}
else if (containingDeclaration instanceof NamespaceDescriptor) {
FqName qualifiedName = ((NamespaceDescriptor) containingDeclaration).getFqName();
else if (containingDeclaration instanceof PackageFragmentDescriptor) {
FqName qualifiedName = ((PackageFragmentDescriptor) containingDeclaration).getFqName();
String packageClassShortName = PackageClassUtils.getPackageClassName(qualifiedName);
String packageClassName = peek.isEmpty() ? packageClassShortName : peek + "/" + packageClassShortName;
return packageClassName + '$' + name;
@@ -240,8 +240,7 @@ public class CodegenBinding {
answer.addAll(files);
for (FqName name : names) {
NamespaceDescriptor namespaceDescriptor = bindingContext.get(BindingContext.FQNAME_TO_NAMESPACE_DESCRIPTOR, name);
Collection<JetFile> jetFiles = bindingContext.get(NAMESPACE_TO_FILES, namespaceDescriptor);
Collection<JetFile> jetFiles = bindingContext.get(PACKAGE_TO_FILES, name);
if (jetFiles != null) {
answer.addAll(jetFiles);
}
@@ -289,6 +288,7 @@ public class CodegenBinding {
return false;
}
// TODO 2 accept ClassDescriptor and simplify
@NotNull
public static Type getAsmType(@NotNull BindingTrace bindingTrace, @NotNull DeclarationDescriptor descriptor) {
descriptor = descriptor.getOriginal();
@@ -304,14 +304,19 @@ public class CodegenBinding {
return asmType;
}
// TODO 2 accept ClassDescriptor and simplify
@NotNull
private static String getAsmTypeImpl(@NotNull BindingTrace bindingTrace, @NotNull DeclarationDescriptor descriptor) {
if (descriptor instanceof PackageFragmentDescriptor) {
throw new IllegalStateException("package is unexpected: " + descriptor);
}
if (descriptor instanceof FunctionDescriptor) {
throw new IllegalStateException("requested fq name for function: " + descriptor);
}
if (descriptor instanceof ModuleDescriptor) {
throw new IllegalStateException("missed something");
throw new IllegalStateException("module is unexpected: " + descriptor);
}
DeclarationDescriptor container = descriptor.getContainingDeclaration();
@@ -319,13 +324,21 @@ public class CodegenBinding {
throw new IllegalStateException("descriptor has no container: " + descriptor);
}
if (container.getContainingDeclaration() instanceof ModuleDescriptor || container instanceof ScriptDescriptor) {
if (container instanceof ScriptDescriptor) {
return descriptor.getName().getIdentifier();
}
String containerInternalName = getAsmType(bindingTrace, container).getInternalName();
if (descriptor instanceof ClassDescriptor && container instanceof ClassDescriptor) {
if (container instanceof PackageFragmentDescriptor) {
String shortName = descriptor.getName().getIdentifier();
FqName fqName = ((PackageFragmentDescriptor) container).getFqName();
return fqName.isRoot() ? shortName : fqName.asString().replace('.', '/') + '/' + shortName;
}
if (descriptor instanceof ClassDescriptor) {
assert container instanceof ClassDescriptor : "Unexpected container: " + container + " for " + descriptor;
String containerInternalName = getAsmType(bindingTrace, container).getInternalName();
ClassDescriptor klass = (ClassDescriptor) descriptor;
if (klass.getKind() == ClassKind.OBJECT || klass.getKind() == ClassKind.CLASS_OBJECT) {
if (isEnumClass(container)) {
@@ -338,9 +351,10 @@ public class CodegenBinding {
return containerInternalName + JvmAbi.CLASS_OBJECT_SUFFIX;
}
}
return containerInternalName + "$" + descriptor.getName().getIdentifier();
}
return containerInternalName + (container instanceof NamespaceDescriptor ? "/" : "$") + descriptor.getName().getIdentifier();
throw new IllegalStateException("neither top-level nor nested class: " + descriptor);
}
public static boolean isVarCapturedInClosure(BindingContext bindingContext, DeclarationDescriptor descriptor) {
@@ -106,7 +106,7 @@ public abstract class CodegenContext<T extends DeclarationDescriptor> {
while (true) {
assert c != null;
DeclarationDescriptor contextDescriptor = c.getContextDescriptor();
if (!(contextDescriptor instanceof ClassDescriptor) && !(contextDescriptor instanceof NamespaceDescriptor)) {
if (!(contextDescriptor instanceof ClassDescriptor) && !(contextDescriptor instanceof PackageFragmentDescriptor)) {
c = c.getParentContext();
}
else {
@@ -157,13 +157,13 @@ public abstract class CodegenContext<T extends DeclarationDescriptor> {
}
@NotNull
public FieldOwnerContext intoNamespace(@NotNull NamespaceDescriptor descriptor) {
return new NamespaceContext(descriptor, this);
public FieldOwnerContext intoPackagePart(@NotNull PackageFragmentDescriptor descriptor) {
return new PackageContext(descriptor, this);
}
@NotNull
public FieldOwnerContext intoNamespaceFacade(@NotNull Type delegateTo, @NotNull NamespaceDescriptor descriptor) {
return new NamespaceFacadeContext(descriptor, this, delegateTo);
public FieldOwnerContext intoPackageFacade(@NotNull Type delegateTo, @NotNull PackageFragmentDescriptor descriptor) {
return new PackageFacadeContext(descriptor, this, delegateTo);
}
@NotNull
@@ -18,13 +18,12 @@ package org.jetbrains.jet.codegen.context;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.asm4.Type;
import org.jetbrains.jet.codegen.OwnerKind;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.descriptors.PackageFragmentDescriptor;
public class NamespaceContext extends FieldOwnerContext<NamespaceDescriptor> {
public NamespaceContext(@NotNull NamespaceDescriptor contextDescriptor, @Nullable CodegenContext parent) {
public class PackageContext extends FieldOwnerContext<PackageFragmentDescriptor> {
public PackageContext(@NotNull PackageFragmentDescriptor contextDescriptor, @Nullable CodegenContext parent) {
super(contextDescriptor, OwnerKind.NAMESPACE, parent, null, null, null);
}
@@ -19,14 +19,14 @@ package org.jetbrains.jet.codegen.context;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.asm4.Type;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.descriptors.PackageFragmentDescriptor;
public class NamespaceFacadeContext extends NamespaceContext {
public class PackageFacadeContext extends PackageContext {
private final Type delegateTo;
public NamespaceFacadeContext(
@NotNull NamespaceDescriptor contextDescriptor,
public PackageFacadeContext(
@NotNull PackageFragmentDescriptor contextDescriptor,
@Nullable CodegenContext parent,
@NotNull Type delegateTo
) {
@@ -75,7 +75,13 @@ public class GenerationState {
@Nullable
private List<ScriptDescriptor> earlierScriptsForReplInterpreter;
public GenerationState(Project project, ClassBuilderFactory builderFactory, BindingContext bindingContext, List<JetFile> files, boolean inlineEnabled) {
public GenerationState(
@NotNull Project project,
@NotNull ClassBuilderFactory builderFactory,
@NotNull BindingContext bindingContext,
@NotNull List<JetFile> files,
boolean inlineEnabled
) {
this(project, builderFactory, Progress.DEAF, bindingContext, files, true, false, true, inlineEnabled);
}
@@ -16,7 +16,6 @@
package org.jetbrains.jet.codegen.state;
import com.google.common.collect.Lists;
import com.intellij.psi.PsiElement;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -30,6 +29,7 @@ import org.jetbrains.jet.codegen.signature.BothSignatureWriter;
import org.jetbrains.jet.codegen.signature.JvmMethodParameterKind;
import org.jetbrains.jet.codegen.signature.JvmMethodParameterSignature;
import org.jetbrains.jet.codegen.signature.JvmMethodSignature;
import org.jetbrains.jet.descriptors.serialization.descriptors.DeserializedPackageMemberScope;
import org.jetbrains.jet.lang.descriptors.*;
import org.jetbrains.jet.lang.psi.*;
import org.jetbrains.jet.lang.resolve.BindingContext;
@@ -37,10 +37,18 @@ import org.jetbrains.jet.lang.resolve.BindingContextUtils;
import org.jetbrains.jet.lang.resolve.BindingTrace;
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
import org.jetbrains.jet.lang.resolve.calls.util.ExpressionAsFunctionDescriptor;
import org.jetbrains.jet.lang.resolve.java.*;
import org.jetbrains.jet.lang.resolve.java.AsmTypeConstants;
import org.jetbrains.jet.lang.resolve.java.JvmAbi;
import org.jetbrains.jet.lang.resolve.java.PackageClassUtils;
import org.jetbrains.jet.lang.resolve.java.descriptor.JavaPackageFragmentDescriptor;
import org.jetbrains.jet.lang.resolve.java.mapping.KotlinToJavaTypesMap;
import org.jetbrains.jet.lang.resolve.java.resolver.JavaPackageFragmentProvider;
import org.jetbrains.jet.lang.resolve.java.scope.JavaClassStaticMembersScope;
import org.jetbrains.jet.lang.resolve.java.scope.JavaPackageScope;
import org.jetbrains.jet.lang.resolve.name.FqName;
import org.jetbrains.jet.lang.resolve.name.FqNameUnsafe;
import org.jetbrains.jet.lang.resolve.name.Name;
import org.jetbrains.jet.lang.resolve.scopes.JetScope;
import org.jetbrains.jet.lang.types.*;
import org.jetbrains.jet.lang.types.lang.KotlinBuiltIns;
@@ -88,8 +96,8 @@ public class JetTypeMapper extends BindingTraceAware {
@NotNull
public Type getOwner(@NotNull DeclarationDescriptor descriptor, @NotNull OwnerKind kind, boolean isInsideModule) {
DeclarationDescriptor containingDeclaration = descriptor.getContainingDeclaration();
if (containingDeclaration instanceof NamespaceDescriptor) {
return asmTypeForNamespace((NamespaceDescriptor) containingDeclaration, descriptor, isInsideModule);
if (containingDeclaration instanceof PackageFragmentDescriptor) {
return asmTypeForPackage((PackageFragmentDescriptor) containingDeclaration, descriptor, isInsideModule);
}
else if (containingDeclaration instanceof ClassDescriptor) {
ClassDescriptor classDescriptor = (ClassDescriptor) containingDeclaration;
@@ -104,84 +112,57 @@ public class JetTypeMapper extends BindingTraceAware {
}
@NotNull
private JavaNamespaceKind getNsKind(@NotNull NamespaceDescriptor ns) {
JavaNamespaceKind javaNamespaceKind = bindingContext.get(JavaBindingContext.JAVA_NAMESPACE_KIND, ns);
Boolean src = bindingContext.get(BindingContext.NAMESPACE_IS_SRC, ns);
if (javaNamespaceKind == null && src == null) {
throw new IllegalStateException("unknown namespace origin: " + ns);
}
if (javaNamespaceKind != null) {
if (javaNamespaceKind == JavaNamespaceKind.CLASS_STATICS && src != null) {
throw new IllegalStateException(
"conflicting namespace " + ns + ": it is both java statics and from src");
}
return javaNamespaceKind;
}
else {
return JavaNamespaceKind.PROPER;
}
}
@NotNull
private Type asmTypeForNamespace(
@NotNull NamespaceDescriptor namespace,
private Type asmTypeForPackage(
@NotNull PackageFragmentDescriptor packageFragment,
@NotNull DeclarationDescriptor descriptor,
boolean insideModule
) {
StringBuilder r = new StringBuilder();
List<DeclarationDescriptor> path = getPathWithoutRootNsAndModule(namespace);
for (DeclarationDescriptor pathElement : path) {
NamespaceDescriptor ns = (NamespaceDescriptor) pathElement;
if (r.length() > 0) {
JavaNamespaceKind nsKind = getNsKind((NamespaceDescriptor) ns.getContainingDeclaration());
if (nsKind == JavaNamespaceKind.PROPER) {
r.append("/");
}
else if (nsKind == JavaNamespaceKind.CLASS_STATICS) {
r.append("$");
}
}
r.append(ns.getName());
}
if (getNsKind(namespace) == JavaNamespaceKind.PROPER) {
if (r.length() > 0) {
r.append("/");
}
JetFile file = BindingContextUtils.getContainingFile(bindingContext, descriptor);
if (insideModule && file != null) {
String internalName = NamespaceCodegen.getNamespacePartInternalName(file);
r.append(internalName.substring(r.length()));
}
else {
r.append(PackageClassUtils.getPackageClassName(namespace.getFqName()));
}
}
if (r.length() == 0) {
throw new IllegalStateException("internal error: failed to generate classname for " + namespace);
}
return Type.getObjectType(r.toString());
return Type.getObjectType(internalNameForPackage(packageFragment, descriptor, insideModule));
}
@NotNull
public static List<DeclarationDescriptor> getPathWithoutRootNsAndModule(@NotNull NamespaceDescriptor descriptor) {
List<DeclarationDescriptor> path = new ArrayList<DeclarationDescriptor>();
DeclarationDescriptor current = descriptor;
while (true) {
if (current instanceof NamespaceDescriptor && DescriptorUtils.isRootNamespace((NamespaceDescriptor) current)) {
return Lists.reverse(path);
private String internalNameForPackage(
@NotNull PackageFragmentDescriptor packageFragment,
@NotNull DeclarationDescriptor descriptor,
boolean insideModule
) {
if (!(packageFragment instanceof JavaPackageFragmentDescriptor) || packageFragment.getMemberScope() instanceof DeserializedPackageMemberScope) {
JetFile file = BindingContextUtils.getContainingFile(bindingContext, descriptor);
if (insideModule && file != null) {
return NamespaceCodegen.getNamespacePartInternalName(file);
}
else {
return PackageClassUtils.getPackageClassFqName(packageFragment.getFqName()).asString().replace('.', '/');
}
path.add(current);
assert current != null : "Namespace must have a parent: " + descriptor;
current = current.getContainingDeclaration();
}
if (!(packageFragment.getMemberScope() instanceof JavaClassStaticMembersScope)) {
throw new IllegalStateException("Unexpected scope: " + packageFragment.getMemberScope().getClass());
}
JavaPackageFragmentProvider javaFragmentProvider = ((JavaPackageFragmentDescriptor) packageFragment).getProvider();
StringBuilder r = new StringBuilder();
for (FqName pathItem : packageFragment.getFqName().parent().path()) {
if (pathItem.isRoot()) {
continue;
}
r.append(pathItem.shortName().asString());
JetScope memberScope = javaFragmentProvider.getOrCreatePackage(pathItem).getMemberScope();
if (memberScope instanceof JavaClassStaticMembersScope) {
r.append("$");
}
else if (memberScope instanceof JavaPackageScope) {
r.append("/");
}
else {
throw new IllegalStateException("Unexpected scope: " + memberScope.getClass());
}
}
r.append(packageFragment.getName().asString());
return r.toString();
}
@NotNull
@@ -473,9 +454,9 @@ public class JetTypeMapper extends BindingTraceAware {
descriptor = mapSignature("invoke", functionDescriptor, true, kind);
calleeType = owner;
}
else if (functionParent instanceof NamespaceDescriptor) {
else if (functionParent instanceof PackageFragmentDescriptor) {
assert !superCall;
owner = asmTypeForNamespace((NamespaceDescriptor) functionParent, functionDescriptor, isInsideModule);
owner = asmTypeForPackage((PackageFragmentDescriptor) functionParent, functionDescriptor, isInsideModule);
ownerForDefaultImpl = ownerForDefaultParam = owner;
invokeOpcode = INVOKESTATIC;
thisClass = null;