Delete ReceiverValueVisitor
This is done because this visitor ties all ReceiverValue's together, which makes descriptors depend on PSI (ReceiverValue -> ReceiverValueVisitor -> ExpressionReceiver -> JetExpression). Descriptors will be available at runtime, but PSI is very heavy, so this dependency should be gotten rid of
This commit is contained in:
committed by
Alexander Udalov
parent
7d64b84c42
commit
6778b38f79
-6
@@ -19,7 +19,6 @@ package org.jetbrains.jet.lang.resolve.calls.autocasts;
|
|||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.receivers.AbstractReceiverValue;
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.AbstractReceiverValue;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverValue;
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverValue;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverValueVisitor;
|
|
||||||
import org.jetbrains.jet.lang.types.JetType;
|
import org.jetbrains.jet.lang.types.JetType;
|
||||||
|
|
||||||
public class AutoCastReceiver extends AbstractReceiverValue {
|
public class AutoCastReceiver extends AbstractReceiverValue {
|
||||||
@@ -41,11 +40,6 @@ public class AutoCastReceiver extends AbstractReceiverValue {
|
|||||||
return original;
|
return original;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return original.accept(visitor, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "(" + original + " as " + getType() + ")";
|
return "(" + original + " as " + getType() + ")";
|
||||||
|
|||||||
+35
-46
@@ -16,15 +16,18 @@
|
|||||||
|
|
||||||
package org.jetbrains.jet.lang.resolve.calls.autocasts;
|
package org.jetbrains.jet.lang.resolve.calls.autocasts;
|
||||||
|
|
||||||
import com.google.common.collect.Lists;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingTrace;
|
import org.jetbrains.jet.lang.resolve.BindingTrace;
|
||||||
import org.jetbrains.jet.lang.resolve.scopes.receivers.*;
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.ExpressionReceiver;
|
||||||
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverValue;
|
||||||
|
import org.jetbrains.jet.lang.resolve.scopes.receivers.ThisReceiver;
|
||||||
import org.jetbrains.jet.lang.types.JetType;
|
import org.jetbrains.jet.lang.types.JetType;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import static org.jetbrains.jet.lang.diagnostics.Errors.AUTOCAST_IMPOSSIBLE;
|
import static org.jetbrains.jet.lang.diagnostics.Errors.AUTOCAST_IMPOSSIBLE;
|
||||||
import static org.jetbrains.jet.lang.resolve.BindingContext.AUTOCAST;
|
import static org.jetbrains.jet.lang.resolve.BindingContext.AUTOCAST;
|
||||||
@@ -37,54 +40,40 @@ public class AutoCastUtils {
|
|||||||
/**
|
/**
|
||||||
* @return variants @param receiverToCast may be cast to according to @param dataFlowInfo, @param receiverToCast itself is NOT included
|
* @return variants @param receiverToCast may be cast to according to @param dataFlowInfo, @param receiverToCast itself is NOT included
|
||||||
*/
|
*/
|
||||||
|
@NotNull
|
||||||
public static List<ReceiverValue> getAutoCastVariants(
|
public static List<ReceiverValue> getAutoCastVariants(
|
||||||
@NotNull final BindingContext bindingContext,
|
@NotNull BindingContext bindingContext,
|
||||||
@NotNull final DataFlowInfo dataFlowInfo, @NotNull ReceiverValue receiverToCast
|
@NotNull DataFlowInfo dataFlowInfo,
|
||||||
|
@NotNull ReceiverValue receiverToCast
|
||||||
) {
|
) {
|
||||||
return receiverToCast.accept(new ReceiverValueVisitor<List<ReceiverValue>, Object>() {
|
if (receiverToCast instanceof ThisReceiver) {
|
||||||
@Override
|
ThisReceiver receiver = (ThisReceiver) receiverToCast;
|
||||||
public List<ReceiverValue> visitNoReceiver(ReceiverValue noReceiver, Object data) {
|
assert receiver.exists();
|
||||||
return Collections.emptyList();
|
DataFlowValue dataFlowValue = DataFlowValueFactory.createDataFlowValue(receiver);
|
||||||
}
|
return collectAutoCastReceiverValues(dataFlowInfo, receiver, dataFlowValue);
|
||||||
|
}
|
||||||
@Override
|
else if (receiverToCast instanceof ExpressionReceiver) {
|
||||||
public List<ReceiverValue> visitTransientReceiver(TransientReceiver receiver, Object data) {
|
ExpressionReceiver receiver = (ExpressionReceiver) receiverToCast;
|
||||||
return Collections.emptyList();
|
DataFlowValue dataFlowValue =
|
||||||
}
|
DataFlowValueFactory.createDataFlowValue(receiver.getExpression(), receiver.getType(), bindingContext);
|
||||||
|
return collectAutoCastReceiverValues(dataFlowInfo, receiver, dataFlowValue);
|
||||||
@Override
|
}
|
||||||
public List<ReceiverValue> visitExtensionReceiver(ExtensionReceiver receiver, Object data) {
|
else if (receiverToCast instanceof AutoCastReceiver) {
|
||||||
return castThis(dataFlowInfo, receiver);
|
return getAutoCastVariants(bindingContext, dataFlowInfo, ((AutoCastReceiver) receiverToCast).getOriginal());
|
||||||
}
|
}
|
||||||
|
return Collections.emptyList();
|
||||||
@Override
|
|
||||||
public List<ReceiverValue> visitClassReceiver(ClassReceiver receiver, Object data) {
|
|
||||||
return castThis(dataFlowInfo, receiver);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public List<ReceiverValue> visitScriptReceiver(ScriptReceiver receiver, Object data) {
|
|
||||||
return Collections.emptyList();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public List<ReceiverValue> visitExpressionReceiver(ExpressionReceiver receiver, Object data) {
|
|
||||||
DataFlowValue dataFlowValue = DataFlowValueFactory.createDataFlowValue(receiver.getExpression(), receiver.getType(),
|
|
||||||
bindingContext);
|
|
||||||
List<ReceiverValue> result = Lists.newArrayList();
|
|
||||||
for (JetType possibleType : dataFlowInfo.getPossibleTypes(dataFlowValue)) {
|
|
||||||
result.add(new AutoCastReceiver(receiver, possibleType, dataFlowValue.isStableIdentifier()));
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
}, null);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static List<ReceiverValue> castThis(@NotNull DataFlowInfo dataFlowInfo, @NotNull ThisReceiver receiver) {
|
@NotNull
|
||||||
assert receiver.exists();
|
private static List<ReceiverValue> collectAutoCastReceiverValues(
|
||||||
List<ReceiverValue> result = Lists.newArrayList();
|
@NotNull DataFlowInfo dataFlowInfo,
|
||||||
for (JetType possibleType : dataFlowInfo.getPossibleTypes(DataFlowValueFactory.createDataFlowValue(receiver))) {
|
@NotNull ReceiverValue receiver,
|
||||||
result.add(new AutoCastReceiver(receiver, possibleType, true));
|
@NotNull DataFlowValue dataFlowValue
|
||||||
|
) {
|
||||||
|
Set<JetType> possibleTypes = dataFlowInfo.getPossibleTypes(dataFlowValue);
|
||||||
|
List<ReceiverValue> result = new ArrayList<ReceiverValue>(possibleTypes.size());
|
||||||
|
for (JetType possibleType : possibleTypes) {
|
||||||
|
result.add(new AutoCastReceiver(receiver, possibleType, dataFlowValue.isStableIdentifier()));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|||||||
+33
-78
@@ -59,44 +59,26 @@ public class DataFlowValueFactory {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static DataFlowValue createDataFlowValue(@NotNull ReceiverValue receiverValue, @NotNull BindingContext bindingContext) {
|
public static DataFlowValue createDataFlowValue(@NotNull ReceiverValue receiverValue, @NotNull BindingContext bindingContext) {
|
||||||
return receiverValue.accept(new ReceiverValueVisitor<DataFlowValue, BindingContext>() {
|
if (receiverValue instanceof TransientReceiver || receiverValue instanceof ScriptReceiver) {
|
||||||
@Override
|
JetType type = receiverValue.getType();
|
||||||
public DataFlowValue visitNoReceiver(ReceiverValue noReceiver, BindingContext data) {
|
boolean nullable = type.isNullable() || TypeUtils.hasNullableSuperType(type);
|
||||||
throw new IllegalArgumentException("No DataFlowValue exists for ReceiverValue.NO_RECEIVER");
|
return new DataFlowValue(receiverValue, type, nullable, Nullability.NOT_NULL);
|
||||||
}
|
}
|
||||||
|
else if (receiverValue instanceof ClassReceiver || receiverValue instanceof ExtensionReceiver) {
|
||||||
@Override
|
return createDataFlowValue((ThisReceiver) receiverValue);
|
||||||
public DataFlowValue visitExtensionReceiver(ExtensionReceiver receiver, BindingContext data) {
|
}
|
||||||
return createDataFlowValue(receiver);
|
else if (receiverValue instanceof ExpressionReceiver) {
|
||||||
}
|
return createDataFlowValue(((ExpressionReceiver) receiverValue).getExpression(), receiverValue.getType(), bindingContext);
|
||||||
|
}
|
||||||
@Override
|
else if (receiverValue instanceof AutoCastReceiver) {
|
||||||
public DataFlowValue visitExpressionReceiver(ExpressionReceiver receiver, BindingContext bindingContext) {
|
return createDataFlowValue(((AutoCastReceiver) receiverValue).getOriginal(), bindingContext);
|
||||||
return createDataFlowValue(receiver.getExpression(), receiver.getType(), bindingContext);
|
}
|
||||||
}
|
else if (receiverValue == ReceiverValue.NO_RECEIVER) {
|
||||||
|
throw new IllegalArgumentException("No DataFlowValue exists for ReceiverValue.NO_RECEIVER");
|
||||||
@Override
|
}
|
||||||
public DataFlowValue visitClassReceiver(ClassReceiver receiver, BindingContext data) {
|
else {
|
||||||
return createDataFlowValue(receiver);
|
throw new UnsupportedOperationException("Unsupported receiver value: " + receiverValue.getClass().getName());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public DataFlowValue visitTransientReceiver(TransientReceiver receiver, BindingContext data) {
|
|
||||||
return createTransientDataFlowValue(receiver);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public DataFlowValue visitScriptReceiver(ScriptReceiver receiver, BindingContext data) {
|
|
||||||
return createTransientDataFlowValue(receiver);
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
|
||||||
private DataFlowValue createTransientDataFlowValue(ReceiverValue receiver) {
|
|
||||||
JetType type = receiver.getType();
|
|
||||||
boolean nullable = type.isNullable() || TypeUtils.hasNullableSuperType(type);
|
|
||||||
return new DataFlowValue(receiver, type, nullable, Nullability.NOT_NULL);
|
|
||||||
}
|
|
||||||
}, bindingContext);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -203,46 +185,19 @@ public class DataFlowValueFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private static IdentifierInfo getIdForImplicitReceiver(@NotNull ReceiverValue receiverValue, @Nullable final JetExpression expression) {
|
private static IdentifierInfo getIdForImplicitReceiver(@NotNull ReceiverValue receiverValue, @Nullable JetExpression expression) {
|
||||||
return receiverValue.accept(new ReceiverValueVisitor<IdentifierInfo, Void>() {
|
if (receiverValue instanceof ThisReceiver) {
|
||||||
|
return getIdForThisReceiver(((ThisReceiver) receiverValue).getDeclarationDescriptor());
|
||||||
@Override
|
}
|
||||||
public IdentifierInfo visitNoReceiver(ReceiverValue noReceiver, Void data) {
|
else if (receiverValue instanceof AutoCastReceiver) {
|
||||||
return null;
|
return getIdForImplicitReceiver(((AutoCastReceiver) receiverValue).getOriginal(), expression);
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
@Override
|
assert !(receiverValue instanceof TransientReceiver)
|
||||||
public IdentifierInfo visitTransientReceiver(TransientReceiver receiver, Void data) {
|
: "Transient receiver is implicit for an explicit expression: " + expression + ". Receiver: " + receiverValue;
|
||||||
assert false: "Transient receiver is implicit for an explicit expression: " + expression + ". Receiver: " + receiver;
|
// For ExpressionReceiver there is an explicit "this" expression and it was analyzed earlier
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public IdentifierInfo visitExtensionReceiver(ExtensionReceiver receiver, Void data) {
|
|
||||||
return getIdForThisReceiver(receiver);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public IdentifierInfo visitExpressionReceiver(ExpressionReceiver receiver, Void data) {
|
|
||||||
// there is an explicit "this" expression and it was analyzed earlier
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public IdentifierInfo visitClassReceiver(ClassReceiver receiver, Void data) {
|
|
||||||
return getIdForThisReceiver(receiver);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public IdentifierInfo visitScriptReceiver(ScriptReceiver receiver, Void data) {
|
|
||||||
return getIdForThisReceiver(receiver);
|
|
||||||
}
|
|
||||||
}, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
|
||||||
private static IdentifierInfo getIdForThisReceiver(@NotNull ThisReceiver thisReceiver) {
|
|
||||||
return getIdForThisReceiver(thisReceiver.getDeclarationDescriptor());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
-5
@@ -45,11 +45,6 @@ public class ClassReceiver implements ThisReceiver {
|
|||||||
return classDescriptor;
|
return classDescriptor;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitClassReceiver(this, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "Class{" + getType() + "}";
|
return "Class{" + getType() + "}";
|
||||||
|
|||||||
-5
@@ -34,11 +34,6 @@ public class ExpressionReceiver extends AbstractReceiverValue implements Receive
|
|||||||
return expression;
|
return expression;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitExpressionReceiver(this, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return getType() + " {" + expression + ": " + expression.getText() + "}";
|
return getType() + " {" + expression + ": " + expression.getText() + "}";
|
||||||
|
|||||||
-5
@@ -36,11 +36,6 @@ public class ExtensionReceiver extends AbstractReceiverValue implements ThisRece
|
|||||||
return descriptor;
|
return descriptor;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitExtensionReceiver(this, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return getType() + "Ext{" + descriptor + "}";
|
return getType() + "Ext{" + descriptor + "}";
|
||||||
|
|||||||
-8
@@ -20,7 +20,6 @@ import org.jetbrains.annotations.NotNull;
|
|||||||
import org.jetbrains.jet.lang.types.JetType;
|
import org.jetbrains.jet.lang.types.JetType;
|
||||||
|
|
||||||
public interface ReceiverValue {
|
public interface ReceiverValue {
|
||||||
|
|
||||||
ReceiverValue NO_RECEIVER = new ReceiverValue() {
|
ReceiverValue NO_RECEIVER = new ReceiverValue() {
|
||||||
@NotNull
|
@NotNull
|
||||||
@Override
|
@Override
|
||||||
@@ -33,11 +32,6 @@ public interface ReceiverValue {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitNoReceiver(this, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "NO_RECEIVER";
|
return "NO_RECEIVER";
|
||||||
@@ -48,6 +42,4 @@ public interface ReceiverValue {
|
|||||||
JetType getType();
|
JetType getType();
|
||||||
|
|
||||||
boolean exists();
|
boolean exists();
|
||||||
|
|
||||||
<R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data);
|
|
||||||
}
|
}
|
||||||
|
|||||||
-31
@@ -1,31 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2010-2013 JetBrains s.r.o.
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package org.jetbrains.jet.lang.resolve.scopes.receivers;
|
|
||||||
|
|
||||||
public interface ReceiverValueVisitor<R, D> {
|
|
||||||
R visitNoReceiver(ReceiverValue noReceiver, D data);
|
|
||||||
|
|
||||||
R visitTransientReceiver(TransientReceiver receiver, D data);
|
|
||||||
|
|
||||||
R visitExtensionReceiver(ExtensionReceiver receiver, D data);
|
|
||||||
|
|
||||||
R visitExpressionReceiver(ExpressionReceiver receiver, D data);
|
|
||||||
|
|
||||||
R visitClassReceiver(ClassReceiver receiver, D data);
|
|
||||||
|
|
||||||
R visitScriptReceiver(ScriptReceiver receiver, D data);
|
|
||||||
}
|
|
||||||
-5
@@ -48,9 +48,4 @@ public class ScriptReceiver implements ThisReceiver {
|
|||||||
public boolean exists() {
|
public boolean exists() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitScriptReceiver(this, data);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
-5
@@ -28,11 +28,6 @@ public class TransientReceiver extends AbstractReceiverValue {
|
|||||||
super(type);
|
super(type);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, D> R accept(@NotNull ReceiverValueVisitor<R, D> visitor, D data) {
|
|
||||||
return visitor.visitTransientReceiver(this, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "{Transient} : " + getType();
|
return "{Transient} : " + getType();
|
||||||
|
|||||||
Reference in New Issue
Block a user