From 23c305834d9e90353a7baf39f435a0a0fd63f3e2 Mon Sep 17 00:00:00 2001 From: Ilya Klyuchnikov Date: Thu, 2 Oct 2014 15:06:03 +0400 Subject: [PATCH] bytecode inference: @Nullable methods are not visible by default IDEA-130063 IDEA-130494 IDEA-130595 IDEA-130706 --- .../ProjectBytecodeAnalysis.java | 28 +++++++++++-------- .../util/resources/misc/registry.properties | 2 ++ 2 files changed, 19 insertions(+), 11 deletions(-) diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/bytecodeAnalysis/ProjectBytecodeAnalysis.java b/java/java-analysis-impl/src/com/intellij/codeInspection/bytecodeAnalysis/ProjectBytecodeAnalysis.java index 610a6fecdaf5..d18e2e2ca01b 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInspection/bytecodeAnalysis/ProjectBytecodeAnalysis.java +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/bytecodeAnalysis/ProjectBytecodeAnalysis.java @@ -17,6 +17,7 @@ package com.intellij.codeInspection.bytecodeAnalysis; import com.intellij.codeInsight.AnnotationUtil; import com.intellij.codeInspection.dataFlow.ControlFlowAnalyzer; +import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.components.ServiceManager; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.progress.ProgressManager; @@ -48,9 +49,11 @@ import static com.intellij.codeInspection.bytecodeAnalysis.Direction.*; public class ProjectBytecodeAnalysis { public static final Logger LOG = Logger.getInstance("#com.intellij.codeInspection.bytecodeAnalysis"); public static final Key INFERRED_ANNOTATION = Key.create("INFERRED_ANNOTATION"); + public static final String NULLABLE_METHOD = "java.annotations.inference.nullable.method"; public static final String NULLABLE_METHOD_TRANSITIVITY = "java.annotations.inference.nullable.method.transitivity"; public static final int EQUATIONS_LIMIT = 1000; private final Project myProject; + private final boolean nullableMethod; private final boolean nullableMethodTransitivity; public static ProjectBytecodeAnalysis getInstance(@NotNull Project project) { @@ -59,6 +62,7 @@ public class ProjectBytecodeAnalysis { public ProjectBytecodeAnalysis(Project project) { myProject = project; + nullableMethod = Registry.is(NULLABLE_METHOD) || ApplicationManager.getApplication().isUnitTestMode(); nullableMethodTransitivity = Registry.is(NULLABLE_METHOD_TRANSITIVITY); } @@ -243,18 +247,20 @@ public class ProjectBytecodeAnalysis { int arity = owner.getParameterList().getParameters().length; BytecodeAnalysisConverter.addMethodAnnotations(solutions, result, key, arity); - final Solver nullableMethodSolver = new Solver(new ELattice(Value.Bot, Value.Null), Value.Bot); - HKey nullableKey = key.updateDirection(BytecodeAnalysisConverter.mkDirectionKey(NullableOut)); - if (nullableMethodTransitivity) { - collectEquations(Collections.singletonList(nullableKey), nullableMethodSolver, equationsCache); - } - else { - collectSingleEquation(nullableKey, nullableMethodSolver, equationsCache); - } + if (nullableMethod) { + final Solver nullableMethodSolver = new Solver(new ELattice(Value.Bot, Value.Null), Value.Bot); + HKey nullableKey = key.updateDirection(BytecodeAnalysisConverter.mkDirectionKey(NullableOut)); + if (nullableMethodTransitivity) { + collectEquations(Collections.singletonList(nullableKey), nullableMethodSolver, equationsCache); + } + else { + collectSingleEquation(nullableKey, nullableMethodSolver, equationsCache); + } - HashMap nullableSolutions = nullableMethodSolver.solve(); - if (nullableSolutions.get(nullableKey) == Value.Null || nullableSolutions.get(nullableKey.negate()) == Value.Null) { - result.nullables.add(key); + HashMap nullableSolutions = nullableMethodSolver.solve(); + if (nullableSolutions.get(nullableKey) == Value.Null || nullableSolutions.get(nullableKey.negate()) == Value.Null) { + result.nullables.add(key); + } } return result; } diff --git a/platform/util/resources/misc/registry.properties b/platform/util/resources/misc/registry.properties index df9999d2221f..815031a41c4f 100644 --- a/platform/util/resources/misc/registry.properties +++ b/platform/util/resources/misc/registry.properties @@ -242,6 +242,8 @@ ide.completion.autopopup.choose.by.enter=true java.completion.make.outer.variables.final=true java.completion.make.outer.variables.final.description=Make variables accessed from inner class final automatically +java.annotations.inference.nullable.method=false +java.annotations.inference.nullable.method.description=Restart is required; infer @Nullable annotation for method results java.annotations.inference.nullable.method.transitivity=true java.annotations.inference.nullable.method.transitivity.description=Restart is required; if a method result is a call to a @Nullable method, reports the caller as @Nullable as well