diff --git a/java/java-impl/src/com/intellij/codeInspection/dataFlow/ControlFlowAnalyzer.java b/java/java-impl/src/com/intellij/codeInspection/dataFlow/ControlFlowAnalyzer.java
index 889f308fd8b1..c3e51a45218d 100644
--- a/java/java-impl/src/com/intellij/codeInspection/dataFlow/ControlFlowAnalyzer.java
+++ b/java/java-impl/src/com/intellij/codeInspection/dataFlow/ControlFlowAnalyzer.java
@@ -1050,10 +1050,10 @@ class ControlFlowAnalyzer extends JavaElementVisitor {
PsiType exprType = expression.getType();
if (TypeConversionUtil.isPrimitiveAndNotNull(expectedType) && TypeConversionUtil.isPrimitiveWrapper(exprType)) {
- addInstruction(new MethodCallInstruction(expression, MethodCallInstruction.MethodType.UNBOXING));
+ addInstruction(new MethodCallInstruction(expression, MethodCallInstruction.MethodType.UNBOXING, expectedType));
}
else if (TypeConversionUtil.isPrimitiveWrapper(expectedType) && TypeConversionUtil.isPrimitiveAndNotNull(exprType)) {
- addInstruction(new MethodCallInstruction(expression, MethodCallInstruction.MethodType.BOXING));
+ addInstruction(new MethodCallInstruction(expression, MethodCallInstruction.MethodType.BOXING, expectedType));
}
else if (exprType != expectedType &&
TypeConversionUtil.isPrimitiveAndNotNull(exprType) &&
diff --git a/java/java-impl/src/com/intellij/codeInspection/dataFlow/StandardInstructionVisitor.java b/java/java-impl/src/com/intellij/codeInspection/dataFlow/StandardInstructionVisitor.java
index 54df852bfbab..14bffccec716 100644
--- a/java/java-impl/src/com/intellij/codeInspection/dataFlow/StandardInstructionVisitor.java
+++ b/java/java-impl/src/com/intellij/codeInspection/dataFlow/StandardInstructionVisitor.java
@@ -229,17 +229,14 @@ public class StandardInstructionVisitor extends InstructionVisitor {
final PsiType type = instruction.getResultType();
final MethodCallInstruction.MethodType methodType = instruction.getMethodType();
- if (type != null && (type instanceof PsiClassType || type.getArrayDimensions() > 0)) {
- return factory.createTypeValueWithNullability(type, myReturnTypeNullability.get(instruction));
- }
-
+
if (methodType == MethodCallInstruction.MethodType.UNBOXING) {
return factory.getBoxedFactory().createUnboxed(qualifierValue);
}
if (methodType == MethodCallInstruction.MethodType.BOXING) {
DfaValue boxed = factory.getBoxedFactory().createBoxed(qualifierValue);
- return boxed == null ? DfaUnknownValue.getInstance() : boxed;
+ return boxed == null ? factory.getNotNullFactory().create(type) : boxed;
}
if (methodType == MethodCallInstruction.MethodType.CAST) {
@@ -248,6 +245,10 @@ public class StandardInstructionVisitor extends InstructionVisitor {
}
return qualifierValue;
}
+
+ if (type != null && (type instanceof PsiClassType || type.getArrayDimensions() > 0)) {
+ return factory.createTypeValueWithNullability(type, myReturnTypeNullability.get(instruction));
+ }
return DfaUnknownValue.getInstance();
}
diff --git a/java/java-impl/src/com/intellij/codeInspection/dataFlow/instructions/MethodCallInstruction.java b/java/java-impl/src/com/intellij/codeInspection/dataFlow/instructions/MethodCallInstruction.java
index 22f98623447d..a46abb680cd6 100644
--- a/java/java-impl/src/com/intellij/codeInspection/dataFlow/instructions/MethodCallInstruction.java
+++ b/java/java-impl/src/com/intellij/codeInspection/dataFlow/instructions/MethodCallInstruction.java
@@ -36,40 +36,35 @@ import org.jetbrains.annotations.Nullable;
public class MethodCallInstruction extends Instruction {
@Nullable private final PsiCallExpression myCall;
- @Nullable private PsiType myType;
+ @Nullable private final PsiType myType;
@NotNull private final PsiExpression[] myArgs;
- private boolean myShouldFlushFields;
+ private final boolean myShouldFlushFields;
@NotNull private final PsiExpression myContext;
private final MethodType myMethodType;
- @Nullable private DfaValue myPrecalculatedReturnValue;
+ @Nullable private final DfaValue myPrecalculatedReturnValue;
public enum MethodType {
BOXING, UNBOXING, REGULAR_METHOD_CALL, CAST
}
- public MethodCallInstruction(@NotNull PsiCallExpression callExpression, @Nullable DfaValue precalculatedReturnValue) {
- this(callExpression, MethodType.REGULAR_METHOD_CALL);
- myPrecalculatedReturnValue = precalculatedReturnValue;
- }
-
public MethodCallInstruction(@NotNull PsiExpression context, MethodType methodType, @Nullable PsiType resultType) {
- this(context, methodType);
- myType = resultType;
- myShouldFlushFields = false;
- }
-
- public MethodCallInstruction(@NotNull PsiExpression context, MethodType methodType) {
myContext = context;
myMethodType = methodType;
- myCall = methodType == MethodType.REGULAR_METHOD_CALL && context instanceof PsiCallExpression ? (PsiCallExpression)context : null;
- final PsiExpressionList argList = myCall == null ? null : myCall.getArgumentList();
+ myCall = null;
+ myArgs = PsiExpression.EMPTY_ARRAY;
+ myType = resultType;
+ myShouldFlushFields = false;
+ myPrecalculatedReturnValue = null;
+ }
+
+ public MethodCallInstruction(@NotNull PsiCallExpression context, @Nullable DfaValue precalculatedReturnValue) {
+ myContext = context;
+ myMethodType = MethodType.REGULAR_METHOD_CALL;
+ myCall = context;
+ final PsiExpressionList argList = context.getArgumentList();
myArgs = argList != null ? argList.getExpressions() : PsiExpression.EMPTY_ARRAY;
-
- myType = myCall == null ? null : myCall.getType();
-
- myShouldFlushFields = true;
- if (myCall instanceof PsiNewExpression && myType != null && myType.getArrayDimensions() > 0) {
- myShouldFlushFields = false;
- }
+ myType = myCall.getType();
+ myShouldFlushFields = !(myCall instanceof PsiNewExpression && myType != null && myType.getArrayDimensions() > 0);
+ myPrecalculatedReturnValue = precalculatedReturnValue;
}
@Nullable
diff --git a/java/java-tests/testData/inspection/dataFlow/fixture/NotNullPrimitive.java b/java/java-tests/testData/inspection/dataFlow/fixture/NotNullPrimitive.java
new file mode 100644
index 000000000000..d76f214bba62
--- /dev/null
+++ b/java/java-tests/testData/inspection/dataFlow/fixture/NotNullPrimitive.java
@@ -0,0 +1,24 @@
+import org.jetbrains.annotations.NotNull;
+
+class Foo {
+ public int getValue() {
+ return 5;
+ }
+
+ public void nullcheck() {
+ Integer x = getValue();
+ System.out.println(x == null ? "NULL" : Integer.toHexString(x));
+ }
+}
+
+class Bar {
+ @NotNull
+ public Integer getValue() {
+ return 5;
+ }
+
+ public void nullcheck() {
+ Integer x = getValue();
+ System.out.println(x == null ? "NULL" : Integer.toHexString(x));
+ }
+}
diff --git a/java/java-tests/testSrc/com/intellij/codeInspection/DataFlowInspectionTest.java b/java/java-tests/testSrc/com/intellij/codeInspection/DataFlowInspectionTest.java
index a9cfa16baf1f..36060cac29b6 100644
--- a/java/java-tests/testSrc/com/intellij/codeInspection/DataFlowInspectionTest.java
+++ b/java/java-tests/testSrc/com/intellij/codeInspection/DataFlowInspectionTest.java
@@ -69,6 +69,7 @@ public class DataFlowInspectionTest extends LightCodeInsightFixtureTestCase {
public void testComparingToNotNullShouldNotAffectNullity() throws Throwable { doTest(); }
public void testStringTernaryAlwaysTrue() throws Throwable { doTest(); }
+ public void testNotNullPrimitive() throws Throwable { doTest(); }
public void testBoxing128() throws Throwable { doTest(); }
public void testFinalFieldsInitializedByAnnotatedParameters() throws Throwable { doTest(); }
public void testMultiCatch() throws Throwable { doTest(); }