KT-394 Make class object members visible inside the owning class
KT-588 Unresolved static method
This commit is contained in:
+20
-5
@@ -5,7 +5,9 @@ import com.google.common.collect.Sets;
|
|||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor;
|
import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor;
|
||||||
import org.jetbrains.jet.lang.resolve.*;
|
import org.jetbrains.jet.lang.resolve.AbstractScopeAdapter;
|
||||||
|
import org.jetbrains.jet.lang.resolve.BindingTrace;
|
||||||
|
import org.jetbrains.jet.lang.resolve.TraceBasedRedeclarationHandler;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.JetScope;
|
import org.jetbrains.jet.lang.resolve.scopes.JetScope;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.SubstitutingScope;
|
import org.jetbrains.jet.lang.resolve.scopes.SubstitutingScope;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
|
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
|
||||||
@@ -43,10 +45,6 @@ public class MutableClassDescriptor extends MutableDeclarationDescriptor impleme
|
|||||||
private JetType superclassType;
|
private JetType superclassType;
|
||||||
private ClassReceiver implicitReceiver;
|
private ClassReceiver implicitReceiver;
|
||||||
|
|
||||||
// public MutableClassDescriptor(@NotNull BindingTrace trace, @NotNull DeclarationDescriptor containingDeclaration, @NotNull JetScope outerScope) {
|
|
||||||
// this(trace, containingDeclaration, outerScope, ClassKind.CLASS);
|
|
||||||
// }
|
|
||||||
|
|
||||||
public MutableClassDescriptor(@NotNull BindingTrace trace, @NotNull DeclarationDescriptor containingDeclaration, @NotNull JetScope outerScope, ClassKind kind) {
|
public MutableClassDescriptor(@NotNull BindingTrace trace, @NotNull DeclarationDescriptor containingDeclaration, @NotNull JetScope outerScope, ClassKind kind) {
|
||||||
super(containingDeclaration);
|
super(containingDeclaration);
|
||||||
TraceBasedRedeclarationHandler redeclarationHandler = new TraceBasedRedeclarationHandler(trace);
|
TraceBasedRedeclarationHandler redeclarationHandler = new TraceBasedRedeclarationHandler(trace);
|
||||||
@@ -66,6 +64,23 @@ public class MutableClassDescriptor extends MutableDeclarationDescriptor impleme
|
|||||||
}
|
}
|
||||||
assert classObjectDescriptor.getKind() == ClassKind.OBJECT;
|
assert classObjectDescriptor.getKind() == ClassKind.OBJECT;
|
||||||
this.classObjectDescriptor = classObjectDescriptor;
|
this.classObjectDescriptor = classObjectDescriptor;
|
||||||
|
|
||||||
|
// Members of the class object are accessible from the class
|
||||||
|
// The scope must be lazy, because classObjectDescriptor may not by fully built yet
|
||||||
|
scopeForMemberResolution.importScope(new AbstractScopeAdapter() {
|
||||||
|
@NotNull
|
||||||
|
@Override
|
||||||
|
protected JetScope getWorkerScope() {
|
||||||
|
return MutableClassDescriptor.this.classObjectDescriptor.getDefaultType().getMemberScope();
|
||||||
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
@Override
|
||||||
|
public ReceiverDescriptor getImplicitReceiver() {
|
||||||
|
return MutableClassDescriptor.this.classObjectDescriptor.getImplicitReceiver();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
);
|
||||||
return ClassObjectStatus.OK;
|
return ClassObjectStatus.OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -98,8 +98,16 @@ import static org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverDescriptor
|
|||||||
}
|
}
|
||||||
doComputeTasks(scope, explicitReceiver, call, name, result, AutoCastService.NO_AUTO_CASTS);
|
doComputeTasks(scope, explicitReceiver, call, name, result, AutoCastService.NO_AUTO_CASTS);
|
||||||
|
|
||||||
ReceiverDescriptor receiverToCast = explicitReceiver.exists() ? explicitReceiver : scope.getImplicitReceiver();
|
List<ReceiverDescriptor> receivers;
|
||||||
if (receiverToCast.exists()) {
|
if (explicitReceiver.exists()) {
|
||||||
|
receivers = Collections.singletonList(explicitReceiver);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
receivers = Lists.newArrayList();
|
||||||
|
scope.getImplicitReceiversHierarchy(receivers);
|
||||||
|
}
|
||||||
|
for (ReceiverDescriptor receiverToCast : receivers) {
|
||||||
|
assert receiverToCast.exists();
|
||||||
doComputeTasks(scope, receiverToCast, call, name, result, new AutoCastServiceImpl(dataFlowInfo, bindingContext));
|
doComputeTasks(scope, receiverToCast, call, name, result, new AutoCastServiceImpl(dataFlowInfo, bindingContext));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
|
|||||||
@@ -232,15 +232,6 @@ public class WritableScopeImpl extends WritableScopeWithImports {
|
|||||||
return super.getClassifier(name);
|
return super.getClassifier(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
|
||||||
@Override
|
|
||||||
public ReceiverDescriptor getImplicitReceiver() {
|
|
||||||
if (implicitReceiver == null) {
|
|
||||||
return super.getImplicitReceiver();
|
|
||||||
}
|
|
||||||
return implicitReceiver;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void addNamespace(@NotNull NamespaceDescriptor namespaceDescriptor) {
|
public void addNamespace(@NotNull NamespaceDescriptor namespaceDescriptor) {
|
||||||
Map<String, DeclarationDescriptor> variableClassOrNamespaceDescriptors = getVariableClassOrNamespaceDescriptors();
|
Map<String, DeclarationDescriptor> variableClassOrNamespaceDescriptors = getVariableClassOrNamespaceDescriptors();
|
||||||
@@ -272,6 +263,15 @@ public class WritableScopeImpl extends WritableScopeWithImports {
|
|||||||
return super.getNamespace(name);
|
return super.getNamespace(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
@Override
|
||||||
|
public ReceiverDescriptor getImplicitReceiver() {
|
||||||
|
if (implicitReceiver == null) {
|
||||||
|
return super.getImplicitReceiver();
|
||||||
|
}
|
||||||
|
return implicitReceiver;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setImplicitReceiver(@NotNull ReceiverDescriptor implicitReceiver) {
|
public void setImplicitReceiver(@NotNull ReceiverDescriptor implicitReceiver) {
|
||||||
if (this.implicitReceiver != null) {
|
if (this.implicitReceiver != null) {
|
||||||
|
|||||||
+15
@@ -7,6 +7,7 @@ import org.jetbrains.jet.lang.descriptors.ClassifierDescriptor;
|
|||||||
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.VariableDescriptor;
|
import org.jetbrains.jet.lang.descriptors.VariableDescriptor;
|
||||||
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverDescriptor;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
@@ -50,6 +51,20 @@ public abstract class WritableScopeWithImports extends JetScopeAdapter implement
|
|||||||
currentIndividualImportScope = null;
|
currentIndividualImportScope = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void getImplicitReceiversHierarchy(@NotNull List<ReceiverDescriptor> result) {
|
||||||
|
super.getImplicitReceiversHierarchy(result);
|
||||||
|
// Imported scopes come with their receivers
|
||||||
|
// Example: class member resolution scope imports a scope of it's class object
|
||||||
|
// members of the class object must be able to find it as an implicit receiver
|
||||||
|
for (JetScope scope : getImports()) {
|
||||||
|
ReceiverDescriptor definedReceiver = scope.getImplicitReceiver();
|
||||||
|
if (definedReceiver.exists()) {
|
||||||
|
result.add(0, definedReceiver);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public VariableDescriptor getVariable(@NotNull String name) {
|
public VariableDescriptor getVariable(@NotNull String name) {
|
||||||
// Meaningful lookup goes here
|
// Meaningful lookup goes here
|
||||||
|
|||||||
+1
-8
@@ -111,13 +111,6 @@ public class ClosureExpressionsTypingVisitor extends ExpressionTypingVisitor {
|
|||||||
private FunctionDescriptorImpl createFunctionDescriptor(JetFunctionLiteralExpression expression, ExpressionTypingContext context, boolean functionTypeExpected) {
|
private FunctionDescriptorImpl createFunctionDescriptor(JetFunctionLiteralExpression expression, ExpressionTypingContext context, boolean functionTypeExpected) {
|
||||||
JetFunctionLiteral functionLiteral = expression.getFunctionLiteral();
|
JetFunctionLiteral functionLiteral = expression.getFunctionLiteral();
|
||||||
JetTypeReference receiverTypeRef = functionLiteral.getReceiverTypeRef();
|
JetTypeReference receiverTypeRef = functionLiteral.getReceiverTypeRef();
|
||||||
final JetType receiverType;
|
|
||||||
if (receiverTypeRef != null) {
|
|
||||||
receiverType = context.getTypeResolver().resolveType(context.scope, receiverTypeRef);
|
|
||||||
} else {
|
|
||||||
ReceiverDescriptor implicitReceiver = context.scope.getImplicitReceiver();
|
|
||||||
receiverType = implicitReceiver.exists() ? implicitReceiver.getType() : null;
|
|
||||||
}
|
|
||||||
FunctionDescriptorImpl functionDescriptor = new FunctionDescriptorImpl(
|
FunctionDescriptorImpl functionDescriptor = new FunctionDescriptorImpl(
|
||||||
context.scope.getContainingDeclaration(), Collections.<AnnotationDescriptor>emptyList(), "<anonymous>");
|
context.scope.getContainingDeclaration(), Collections.<AnnotationDescriptor>emptyList(), "<anonymous>");
|
||||||
|
|
||||||
@@ -133,7 +126,7 @@ public class ClosureExpressionsTypingVisitor extends ExpressionTypingVisitor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
effectiveReceiverType = receiverType;
|
effectiveReceiverType = context.getTypeResolver().resolveType(context.scope, receiverTypeRef);
|
||||||
}
|
}
|
||||||
functionDescriptor.initialize(effectiveReceiverType, NO_RECEIVER, Collections.<TypeParameterDescriptor>emptyList(), valueParameterDescriptors, null, Modality.FINAL, Visibility.LOCAL);
|
functionDescriptor.initialize(effectiveReceiverType, NO_RECEIVER, Collections.<TypeParameterDescriptor>emptyList(), valueParameterDescriptors, null, Modality.FINAL, Visibility.LOCAL);
|
||||||
context.trace.record(BindingContext.FUNCTION, expression, functionDescriptor);
|
context.trace.record(BindingContext.FUNCTION, expression, functionDescriptor);
|
||||||
|
|||||||
@@ -0,0 +1,11 @@
|
|||||||
|
// KT-394 Make class object members visible inside the owning class
|
||||||
|
|
||||||
|
class X() {
|
||||||
|
// class Y {}
|
||||||
|
|
||||||
|
class object{
|
||||||
|
class Y() {}
|
||||||
|
}
|
||||||
|
|
||||||
|
val y : Y = Y()
|
||||||
|
}
|
||||||
@@ -0,0 +1,12 @@
|
|||||||
|
// KT-588 Unresolved static method
|
||||||
|
class Test() : Thread("Test") {
|
||||||
|
class object {
|
||||||
|
fun init2() {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
override fun run() {
|
||||||
|
init2() // unresolved
|
||||||
|
Test.init2() // ok
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user