mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
DFA: support value escaping on custom objects (IDEA-188303)
This commit is contained in:
+3
@@ -582,6 +582,9 @@ public class StandardInstructionVisitor extends InstructionVisitor {
|
||||
}
|
||||
}
|
||||
DfaValue value = factory.createTypeValue(type, nullability);
|
||||
if (!instruction.shouldFlushFields() && instruction.getContext() instanceof PsiNewExpression) {
|
||||
value = factory.withFact(value, DfaFactType.LOCALITY, true);
|
||||
}
|
||||
return factory.withFact(value, DfaFactType.MUTABILITY, mutable);
|
||||
}
|
||||
LongRangeSet range = LongRangeSet.fromType(type);
|
||||
|
||||
+19
-5
@@ -24,9 +24,7 @@ import com.siyeh.ig.callMatcher.CallMatcher;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.*;
|
||||
|
||||
|
||||
public class MethodCallInstruction extends Instruction {
|
||||
@@ -198,8 +196,24 @@ public class MethodCallInstruction extends Instruction {
|
||||
}
|
||||
|
||||
private boolean isPureCall() {
|
||||
if (myTargetMethod == null) return false;
|
||||
return ControlFlowAnalyzer.isPure(myTargetMethod) || SpecialField.findSpecialField(myTargetMethod) != null;
|
||||
if (myTargetMethod != null) {
|
||||
return ControlFlowAnalyzer.isPure(myTargetMethod) || SpecialField.findSpecialField(myTargetMethod) != null;
|
||||
}
|
||||
if (!(myContext instanceof PsiNewExpression)) return false;
|
||||
PsiNewExpression newExpression = (PsiNewExpression)myContext;
|
||||
if (newExpression.getArgumentList() == null || !newExpression.getArgumentList().isEmpty()) return false;
|
||||
PsiJavaCodeReferenceElement classReference = newExpression.getClassReference();
|
||||
if (classReference == null) return false;
|
||||
PsiClass clazz = ObjectUtils.tryCast(classReference.resolve(), PsiClass.class);
|
||||
if (clazz == null) return false;
|
||||
Set<PsiClass> visited = new HashSet<>();
|
||||
while (true) {
|
||||
for (PsiMethod ctor : clazz.getConstructors()) {
|
||||
if(ctor.getParameterList().isEmpty()) return ControlFlowAnalyzer.isPure(ctor);
|
||||
}
|
||||
clazz = clazz.getSuperClass();
|
||||
if (clazz == null || !visited.add(clazz)) return false;
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
import java.util.*;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
class ObjectLocality {
|
||||
int x;
|
||||
|
||||
void test() {
|
||||
ObjectLocality o = new ObjectLocality();
|
||||
o.x = 5;
|
||||
unknown();
|
||||
<warning descr="Variable is already assigned to this value">o.x</warning> = 5;
|
||||
o.unknown();
|
||||
o.x = 5;
|
||||
}
|
||||
|
||||
native void unknown();
|
||||
}
|
||||
@@ -609,4 +609,5 @@ public class DataFlowInspectionTest extends DataFlowInspectionTestCase {
|
||||
}
|
||||
public void testMergedInitializerAndConstructor() { doTest(); }
|
||||
public void testClassMethodsInlining() { doTest(); }
|
||||
public void testObjectLocality() { doTest(); }
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user