diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/codeInspection/unusedDef/UnusedDefInspection.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/codeInspection/unusedDef/UnusedDefInspection.java index 6f0aa265a5a9..5468100a25b4 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/codeInspection/unusedDef/UnusedDefInspection.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/codeInspection/unusedDef/UnusedDefInspection.java @@ -15,25 +15,35 @@ */ package org.jetbrains.plugins.groovy.codeInspection.unusedDef; -import com.intellij.codeInspection.*; +import com.intellij.codeInspection.ProblemHighlightType; +import com.intellij.codeInspection.ProblemsHolder; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiReference; -import com.intellij.psi.util.PsiTreeUtil; -import com.intellij.psi.search.searches.ReferencesSearch; import com.intellij.psi.search.LocalSearchScope; +import com.intellij.psi.search.searches.ReferencesSearch; +import com.intellij.psi.util.PsiTreeUtil; import com.intellij.util.Processor; -import gnu.trove.*; -import org.jetbrains.annotations.*; +import gnu.trove.TIntHashSet; +import gnu.trove.TIntObjectHashMap; +import gnu.trove.TIntProcedure; +import gnu.trove.TObjectProcedure; +import org.jetbrains.annotations.Nls; +import org.jetbrains.annotations.NonNls; +import org.jetbrains.annotations.NotNull; import org.jetbrains.plugins.groovy.codeInspection.GroovyInspectionBundle; import org.jetbrains.plugins.groovy.codeInspection.GroovyLocalInspectionBase; -import org.jetbrains.plugins.groovy.lang.psi.*; +import org.jetbrains.plugins.groovy.lang.psi.GrControlFlowOwner; +import org.jetbrains.plugins.groovy.lang.psi.GroovyFileBase; +import org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrClassInitializer; import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrField; import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariable; -import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrClassInitializer; import org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrClosableBlock; -import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrAssignmentExpression; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrPostfixExpression; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression; import org.jetbrains.plugins.groovy.lang.psi.api.statements.params.GrParameter; -import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.*; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod; import org.jetbrains.plugins.groovy.lang.psi.controlFlow.Instruction; import org.jetbrains.plugins.groovy.lang.psi.controlFlow.ReadWriteVariableInstruction; import org.jetbrains.plugins.groovy.lang.psi.dataFlow.DFAEngine; @@ -105,22 +115,27 @@ public class UnusedDefInspection extends GroovyLocalInspectionBase { unusedDefs.forEach(new TIntProcedure() { public boolean execute(int num) { - final ReadWriteVariableInstruction instruction = (ReadWriteVariableInstruction) flow[num]; + final ReadWriteVariableInstruction instruction = (ReadWriteVariableInstruction)flow[num]; final PsiElement element = instruction.getElement(); + if (element == null) return true; + PsiElement toHighlight = null; if (isLocalAssignment(element) && isUsedInToplevelFlowOnly(element)) { if (element instanceof GrReferenceExpression) { PsiElement parent = element.getParent(); - PsiElement toHighlight = null; if (parent instanceof GrAssignmentExpression) { - toHighlight = ((GrAssignmentExpression) parent).getLValue(); - } if (parent instanceof GrPostfixExpression) { + toHighlight = ((GrAssignmentExpression)parent).getRValue(); + } + if (parent instanceof GrPostfixExpression) { toHighlight = parent; } - if (toHighlight == null) toHighlight = element; - problemsHolder.registerProblem(toHighlight, GroovyInspectionBundle.message("unused.assignment.tooltip"), ProblemHighlightType.LIKE_UNUSED_SYMBOL); - } else if (element instanceof GrVariable) { - problemsHolder.registerProblem(((GrVariable) element).getNameIdentifierGroovy(), GroovyInspectionBundle.message("unused.assignment.tooltip"), ProblemHighlightType.LIKE_UNUSED_SYMBOL); } + else if (element instanceof GrVariable) { + toHighlight = ((GrVariable)element).getInitializerGroovy(); + if (toHighlight == null) toHighlight = ((GrVariable)element).getNameIdentifierGroovy(); + } + if (toHighlight == null) toHighlight = element; + problemsHolder.registerProblem(toHighlight, GroovyInspectionBundle.message("unused.assignment.tooltip"), + ProblemHighlightType.LIKE_UNUSED_SYMBOL); } return true; } diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/controlFlow/impl/ControlFlowBuilder.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/controlFlow/impl/ControlFlowBuilder.java index 102e34cde437..ea85bc7a40b1 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/controlFlow/impl/ControlFlowBuilder.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/controlFlow/impl/ControlFlowBuilder.java @@ -39,6 +39,7 @@ import org.jetbrains.plugins.groovy.lang.psi.api.statements.clauses.GrForInClaus import org.jetbrains.plugins.groovy.lang.psi.api.statements.clauses.GrTraditionalForClause; import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.*; import org.jetbrains.plugins.groovy.lang.psi.api.statements.params.GrParameter; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.GrAnonymousClassDefinition; import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.GrTypeDefinition; import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod; import org.jetbrains.plugins.groovy.lang.psi.controlFlow.*; @@ -60,7 +61,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } - private class ExceptionInfo { + private static class ExceptionInfo { GrCatchClause myClause; List myThrowers = new ArrayList(); @@ -181,7 +182,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { myHead = instruction; } - void addEdge(InstructionImpl beg, InstructionImpl end) { + static void addEdge(InstructionImpl beg, InstructionImpl end) { if (!beg.mySucc.contains(end)) { beg.mySucc.add(end); } @@ -281,7 +282,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { @Nullable private ExceptionInfo findCatch(PsiType thrownType) { for (int i = myCatchedExceptionInfos.size() - 1; i >= 0; i--) { - final ControlFlowBuilder.ExceptionInfo info = myCatchedExceptionInfos.get(i); + final ExceptionInfo info = myCatchedExceptionInfos.get(i); final GrCatchClause clause = info.myClause; final GrParameter parameter = clause.getParameter(); if (parameter != null) { @@ -363,7 +364,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } } - private boolean isIncOrDecOperand(GrReferenceExpression referenceExpression) { + private static boolean isIncOrDecOperand(GrReferenceExpression referenceExpression) { final PsiElement parent = referenceExpression.getParent(); if (parent instanceof GrPostfixExpression) return true; if (parent instanceof GrUnaryExpression) { @@ -667,6 +668,9 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } public void visitTypeDefinition(GrTypeDefinition typeDefinition) { + if (typeDefinition instanceof GrAnonymousClassDefinition) { + super.visitTypeDefinition(typeDefinition); + } } public void visitVariable(GrVariable variable) { @@ -678,6 +682,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } } + @Nullable private InstructionImpl findInstruction(PsiElement element) { for (int i = myProcessingStack.size() - 1; i >= 0; i--) { InstructionImpl instruction = myProcessingStack.get(i); @@ -686,7 +691,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { return null; } - class CallInstructionImpl extends InstructionImpl implements CallInstruction { + static class CallInstructionImpl extends InstructionImpl implements CallInstruction { private final InstructionImpl myCallee; public String toString() { @@ -712,7 +717,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } } - class PostCallInstructionImpl extends InstructionImpl implements AfterCallInstruction { + static class PostCallInstructionImpl extends InstructionImpl implements AfterCallInstruction { private final CallInstructionImpl myCall; private RetInstruction myReturnInsn; @@ -743,7 +748,7 @@ public class ControlFlowBuilder extends GroovyRecursiveElementVisitor { } } - class RetInstruction extends InstructionImpl { + static class RetInstruction extends InstructionImpl { RetInstruction(int num) { super(null, num); } diff --git a/plugins/groovy/testdata/highlighting/IfIncrementElseReturn.groovy b/plugins/groovy/testdata/highlighting/IfIncrementElseReturn.groovy index 04e1d86bc2e5..7067d0b17666 100644 --- a/plugins/groovy/testdata/highlighting/IfIncrementElseReturn.groovy +++ b/plugins/groovy/testdata/highlighting/IfIncrementElseReturn.groovy @@ -10,4 +10,4 @@ int numPermutationsPrinted = 1; } -def x = 2 \ No newline at end of file +def x = 2 \ No newline at end of file diff --git a/plugins/groovy/testdata/highlighting/PrefixIncrementCfa.groovy b/plugins/groovy/testdata/highlighting/PrefixIncrementCfa.groovy index 711bb7b8c062..2fd6f971ca1f 100644 --- a/plugins/groovy/testdata/highlighting/PrefixIncrementCfa.groovy +++ b/plugins/groovy/testdata/highlighting/PrefixIncrementCfa.groovy @@ -1,5 +1,5 @@ int idx -idx = 2 +idx = 2 idx = 3 if (++idx == 8) { //Assignment is used here idx = 33 diff --git a/plugins/groovy/testdata/highlighting/UnusedVariable.groovy b/plugins/groovy/testdata/highlighting/UnusedVariable.groovy index 0ea69f992bde..bf0f533ac9c8 100644 --- a/plugins/groovy/testdata/highlighting/UnusedVariable.groovy +++ b/plugins/groovy/testdata/highlighting/UnusedVariable.groovy @@ -1 +1 @@ -Class clazz = null \ No newline at end of file +Class clazz = null \ No newline at end of file