From 9e0bef7dcd439529eb87725f9b26ed26cb0b2baa Mon Sep 17 00:00:00 2001 From: Roman Shevchenko Date: Thu, 24 Feb 2011 19:53:10 +0100 Subject: [PATCH] Project Coin try-with-resource support, take 4 --- .../intellij/codeInsight/ExceptionUtil.java | 6 +- .../analysis/HighlightControlFlowUtil.java | 4 +- .../daemon/impl/analysis/HighlightUtil.java | 6 +- .../impl/analysis/HighlightVisitorImpl.java | 9 +- .../quickfix/ReuseVariableDeclarationFix.java | 4 +- .../defUse/DefUseInspection.java | 2 +- .../lang/java/parser/DeclarationParser.java | 116 +++++++++--------- .../psi/controlFlow/ControlFlowAnalyzer.java | 21 +--- .../intellij/psi/controlFlow/DefUseUtil.java | 10 +- .../com/intellij/psi/impl/PsiImplUtil.java | 9 +- .../psi/impl/PsiJavaParserFacadeImpl.java | 6 +- .../psi/impl/source/PsiModifierListImpl.java | 5 +- .../psi/impl/source/tree/JavaElementType.java | 2 +- .../tree/java/PsiLocalVariableImpl.java | 27 ++-- .../source/tree/java/PsiResourceImpl.java | 74 ----------- .../source/tree/java/PsiResourceListImpl.java | 4 +- .../tree/java/PsiResourceVariableImpl.java | 70 +++++++++++ .../advHighlighting7/TryWithResources.java | 14 +-- .../TryWithResourcesWarn.java | 31 ++--- .../statements/TryIncomplete10.txt | 2 + .../statements/TryIncomplete11.txt | 2 +- .../statements/TryIncomplete12.txt | 2 - .../statements/TryIncomplete13.txt | 6 +- .../statements/TryIncomplete14.txt | 6 +- .../statements/TryIncomplete15.txt | 25 ++-- .../statements/TryIncomplete16.txt | 29 +++-- .../statements/TryIncomplete17.txt | 36 +++--- .../parser-partial/statements/TryNormal4.txt | 31 +++-- .../parser-partial/statements/TryNormal5.txt | 62 +++++----- .../parser-partial/statements/TryNormal6.txt | 23 +++- .../parser-partial/statements/TryNormal7.txt | 19 --- .../daemon/LightAdvHighlightingJdk7Test.java | 3 +- .../parser/partial/StatementParserTest.java | 5 +- .../com/intellij/psi/JavaElementVisitor.java | 4 +- .../com/intellij/psi/PsiJavaParserFacade.java | 2 +- .../src/com/intellij/psi/PsiResource.java | 39 ------ .../src/com/intellij/psi/PsiResourceList.java | 2 +- ...Variable.java => PsiResourceVariable.java} | 13 +- 38 files changed, 316 insertions(+), 415 deletions(-) delete mode 100644 java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceImpl.java create mode 100644 java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceVariableImpl.java delete mode 100644 java/java-tests/testData/psi/parser-partial/statements/TryNormal7.txt delete mode 100644 java/openapi/src/com/intellij/psi/PsiResource.java rename java/openapi/src/com/intellij/psi/{PsiScopedLocalVariable.java => PsiResourceVariable.java} (73%) diff --git a/java/java-impl/src/com/intellij/codeInsight/ExceptionUtil.java b/java/java-impl/src/com/intellij/codeInsight/ExceptionUtil.java index 64fe99852282..08753166bdd4 100644 --- a/java/java-impl/src/com/intellij/codeInsight/ExceptionUtil.java +++ b/java/java-impl/src/com/intellij/codeInsight/ExceptionUtil.java @@ -246,8 +246,8 @@ public class ExceptionUtil { unhandledExceptions = unhandled; } - if (element instanceof PsiResource) { - final List unhandled = getUnhandledCloserExceptions((PsiResource)element, topElement); + if (element instanceof PsiResourceVariable) { + final List unhandled = getUnhandledCloserExceptions((PsiResourceVariable)element, topElement); if (unhandledExceptions == null) { unhandledExceptions = unhandled; } @@ -331,7 +331,7 @@ public class ExceptionUtil { } @NotNull - public static List getUnhandledCloserExceptions(final PsiResource resource, final PsiElement topElement) { + public static List getUnhandledCloserExceptions(final PsiResourceVariable resource, final PsiElement topElement) { final PsiType resourceType = resource.getType(); if (resourceType instanceof PsiClassType) { final PsiClass resourceClass = ((PsiClassType)resourceType).resolve(); diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightControlFlowUtil.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightControlFlowUtil.java index 83704c2c63be..1785837da3a2 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightControlFlowUtil.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightControlFlowUtil.java @@ -675,8 +675,8 @@ public class HighlightControlFlowUtil { @Nullable public static PsiClass getInnerClassVariableReferencedFrom(PsiVariable variable, PsiElement context) { PsiElement[] scope; - if (variable instanceof PsiScopedLocalVariable) { - scope = ((PsiScopedLocalVariable)variable).getDeclarationScope(); + if (variable instanceof PsiResourceVariable) { + scope = ((PsiResourceVariable)variable).getDeclarationScope(); } else if (variable instanceof PsiLocalVariable) { scope = new PsiElement[]{variable.getParent().getParent()}; // code block or for statement diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightUtil.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightUtil.java index 70db6cf0ce8b..df75fdf060e8 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightUtil.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightUtil.java @@ -435,7 +435,7 @@ public class HighlightUtil { @Nullable static HighlightInfo checkVariableInitializerType(PsiVariable variable) { PsiExpression initializer = variable.getInitializer(); - // array initalizer checked in checkArrayInitializerApplicable + // array initializer checked in checkArrayInitializerApplicable if (initializer == null || initializer instanceof PsiArrayInitializerExpression) return null; PsiType lType = variable.getType(); PsiType rType = initializer.getType(); @@ -655,7 +655,7 @@ public class HighlightUtil { } @Nullable - public static HighlightInfo checkUnhandledCloserExceptions(final PsiResource resource) { + public static HighlightInfo checkUnhandledCloserExceptions(final PsiResourceVariable resource) { final List unhandled = ExceptionUtil.getUnhandledCloserExceptions(resource, null); if (unhandled.isEmpty()) return null; @@ -1148,7 +1148,7 @@ public class HighlightUtil { } @Nullable - public static HighlightInfo checkTryResourceIsAutoCloseable(@NotNull final PsiResource resource) { + public static HighlightInfo checkTryResourceIsAutoCloseable(@NotNull final PsiResourceVariable resource) { final PsiType type = resource.getType(); if (type == null) return null; diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java index decc5b2d7126..7ca8e460bdac 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java @@ -906,11 +906,10 @@ public class HighlightVisitorImpl extends JavaElementVisitor implements Highligh } @Override - public void visitResource(final PsiResource resource) { - myHolder.add(HighlightUtil.checkTryResourceIsAutoCloseable(resource)); - if (!myHolder.hasErrorResults()) { - myHolder.add(HighlightUtil.checkUnhandledCloserExceptions(resource)); - } + public void visitResourceVariable(final PsiResourceVariable resourceVariable) { + visitVariable(resourceVariable); + if (!myHolder.hasErrorResults()) myHolder.add(HighlightUtil.checkTryResourceIsAutoCloseable(resourceVariable)); + if (!myHolder.hasErrorResults()) myHolder.add(HighlightUtil.checkUnhandledCloserExceptions(resourceVariable)); } @Override public void visitTypeElement(PsiTypeElement type) { diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/quickfix/ReuseVariableDeclarationFix.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/quickfix/ReuseVariableDeclarationFix.java index 0e6cd0ae748e..2a681620886f 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/quickfix/ReuseVariableDeclarationFix.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/quickfix/ReuseVariableDeclarationFix.java @@ -57,7 +57,7 @@ public class ReuseVariableDeclarationFix implements IntentionAction { return myVariable != null && myVariable.isValid() && myVariable instanceof PsiLocalVariable && - !(myVariable.getParent() instanceof PsiResource && myVariable.getInitializer() == null) && + !(myVariable.getParent() instanceof PsiResourceVariable && myVariable.getInitializer() == null) && previousVariable != null && Comparing.equal(previousVariable.getType(), myVariable.getType()) && myIdentifier != null && @@ -82,7 +82,7 @@ public class ReuseVariableDeclarationFix implements IntentionAction { final PsiElementFactory factory = JavaPsiFacade.getInstance(myVariable.getProject()).getElementFactory(); final PsiElement replacement; final PsiElement parent = myVariable.getParent(); - if (parent instanceof PsiResource) { + if (parent instanceof PsiResourceVariable) { replacement = factory.createResourceFromText(myVariable.getName() + " = " + initializer.getText(), null); } else { diff --git a/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java b/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java index 34293268c478..106d6b6f4b3f 100644 --- a/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java +++ b/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java @@ -97,7 +97,7 @@ public class DefUseInspection extends BaseLocalInspectionTool { PsiElement context = info.getContext(); PsiVariable psiVariable = info.getVariable(); - if (context instanceof PsiDeclarationStatement || context instanceof PsiResource) { + if (context instanceof PsiDeclarationStatement || context instanceof PsiResourceVariable) { if (!info.isRead()) { if (!isOnTheFly) { holder.registerProblem(psiVariable.getNameIdentifier(), diff --git a/java/java-impl/src/com/intellij/lang/java/parser/DeclarationParser.java b/java/java-impl/src/com/intellij/lang/java/parser/DeclarationParser.java index b162024dcd20..7ee229f840a5 100644 --- a/java/java-impl/src/com/intellij/lang/java/parser/DeclarationParser.java +++ b/java/java-impl/src/com/intellij/lang/java/parser/DeclarationParser.java @@ -36,7 +36,7 @@ import static com.intellij.lang.java.parser.JavaParserUtil.exprType; public class DeclarationParser { public enum Context { - FILE, CLASS, CODE_BLOCK, ANNOTATION_INTERFACE, RESOURCE_LIST + FILE, CLASS, CODE_BLOCK, ANNOTATION_INTERFACE } private static final TokenSet AFTER_END_DECLARATION_SET = TokenSet.create(JavaElementType.FIELD, JavaElementType.METHOD); @@ -223,7 +223,7 @@ public class DeclarationParser { if (tokenType == null) return null; if (tokenType == JavaTokenType.LBRACE) { - if (context == Context.FILE || context == Context.CODE_BLOCK || context == Context.RESOURCE_LIST) return null; + if (context == Context.FILE || context == Context.CODE_BLOCK) return null; } else if (tokenType == JavaTokenType.IDENTIFIER || ElementType.PRIMITIVE_TYPE_BIT_SET.contains(tokenType)) { if (context == Context.FILE) return null; @@ -235,7 +235,7 @@ public class DeclarationParser { else if (!ElementType.MODIFIER_BIT_SET.contains(tokenType) && !ElementType.CLASS_KEYWORD_BIT_SET.contains(tokenType) && tokenType != JavaTokenType.AT && - (context == Context.CODE_BLOCK || context == Context.RESOURCE_LIST || tokenType != JavaTokenType.LT)) { + (context == Context.CODE_BLOCK || tokenType != JavaTokenType.LT)) { return null; } @@ -279,7 +279,7 @@ public class DeclarationParser { final PsiBuilder.Marker idPos = builder.mark(); type = parseTypeNotNull(builder); if (builder.getTokenType() == JavaTokenType.LPARENTH) { // constructor - if (context == Context.CODE_BLOCK || context == Context.RESOURCE_LIST) { + if (context == Context.CODE_BLOCK) { declaration.rollbackTo(); return null; } @@ -302,10 +302,6 @@ public class DeclarationParser { declaration.drop(); return modList; } - else if (context == Context.RESOURCE_LIST) { - declaration.rollbackTo(); - return null; - } final PsiBuilder.Marker codeBlock = StatementParser.parseCodeBlock(builder); assert codeBlock != null : builder.getOriginalText(); @@ -331,7 +327,7 @@ public class DeclarationParser { } if (!expect(builder, JavaTokenType.IDENTIFIER)) { - if ((context == Context.CODE_BLOCK || context == Context.RESOURCE_LIST) && modListInfo.second) { + if ((context == Context.CODE_BLOCK) && modListInfo.second) { declaration.rollbackTo(); return null; } @@ -473,11 +469,11 @@ public class DeclarationParser { PsiBuilder.Marker invalidElements = null; String errorMessage = null; boolean delimiterExpected = false; - int elementCount = 0; + boolean noElements = true; while (true) { final IElementType tokenType = builder.getTokenType(); if (tokenType == null || tokenType == JavaTokenType.RPARENTH || tokenType == JavaTokenType.LBRACE) { - boolean noLastElement = !delimiterExpected && elementCount > 0; + final boolean noLastElement = !delimiterExpected && (!noElements && !resources || noElements && resources); if (noLastElement) { error(builder, JavaErrorMessages.message("expected.identifier.or.type")); } @@ -486,13 +482,10 @@ public class DeclarationParser { invalidElements.error(errorMessage); invalidElements = null; } - else if (resources && elementCount == 0) { - error(builder, JavaErrorMessages.message("expected.resource")); - } builder.advanceLexer(); } else { - if (!noLastElement) { + if (!noLastElement || resources) { if (invalidElements != null) { invalidElements.error(errorMessage); } @@ -522,7 +515,7 @@ public class DeclarationParser { invalidElements.errorBefore(errorMessage, listElement); invalidElements = null; } - elementCount++; + noElements= false; continue; } } @@ -531,6 +524,9 @@ public class DeclarationParser { if (builder.getTokenType() == delimiter) { error(builder, noElementMsg); builder.advanceLexer(); + if (noElements && resources) { + noElements = false; + } continue; } else { @@ -556,6 +552,19 @@ public class DeclarationParser { @Nullable public static PsiBuilder.Marker parseParameter(final PsiBuilder builder, final boolean ellipsis, final boolean disjunctiveType) { + return parseListElement(builder, ellipsis, disjunctiveType, false); + } + + @Nullable + public static PsiBuilder.Marker parseResource(final PsiBuilder builder) { + return parseListElement(builder, false, false, true); + } + + @Nullable + private static PsiBuilder.Marker parseListElement(final PsiBuilder builder, + final boolean ellipsis, + final boolean disjunctiveType, + final boolean resource) { final PsiBuilder.Marker param = builder.mark(); final Pair modListInfo = parseModifierList(builder); @@ -577,34 +586,26 @@ public class DeclarationParser { } if (expect(builder, JavaTokenType.IDENTIFIER)) { - eatBrackets(builder, typeInfo != null && typeInfo.isVarArg, JavaErrorMessages.message("expected.rparen")); - done(param, JavaElementType.PARAMETER); - return param; + if (!resource) { + eatBrackets(builder, typeInfo != null && typeInfo.isVarArg, JavaErrorMessages.message("expected.rparen")); + done(param, JavaElementType.PARAMETER); + return param; + } } else { error(builder, JavaErrorMessages.message("expected.identifier")); param.drop(); return modListInfo.first; } - } - @Nullable - public static PsiBuilder.Marker parseResource(final PsiBuilder builder) { - PsiBuilder.Marker element = parse(builder, Context.RESOURCE_LIST); - if (exprType(element) == JavaElementType.MODIFIER_LIST) { - return element; - } - else if (element == null) { - element = ExpressionParser.parse(builder); + if (expectOrError(builder, JavaTokenType.EQ, JavaErrorMessages.message("expected.eq"))) { + if (ExpressionParser.parse(builder) == null) { + error(builder, JavaErrorMessages.message("expected.expression")); + } } - if (element != null) { - final PsiBuilder.Marker resource = element.precede(); - done(resource, JavaElementType.RESOURCE); - return resource; - } - - return null; + done(param, JavaElementType.RESOURCE_VARIABLE); + return param; } @Nullable @@ -614,7 +615,7 @@ public class DeclarationParser { if (context == Context.CLASS || context == Context.ANNOTATION_INTERFACE) { varType = JavaElementType.FIELD; } - else if (context == Context.CODE_BLOCK || context == Context.RESOURCE_LIST) { + else if (context == Context.CODE_BLOCK) { varType = JavaElementType.LOCAL_VARIABLE; } else { @@ -645,11 +646,6 @@ public class DeclarationParser { unclosed = true; break; } - if (context == Context.RESOURCE_LIST) break; - } - else if (context == Context.RESOURCE_LIST) { - error(builder, JavaErrorMessages.message("expected.eq")); - break; } if (builder.getTokenType() != JavaTokenType.COMMA) break; @@ -668,28 +664,26 @@ public class DeclarationParser { builder.advanceLexer(); } - if (context != Context.RESOURCE_LIST) { - if (builder.getTokenType() == JavaTokenType.SEMICOLON && eatSemicolon) { - builder.advanceLexer(); + if (builder.getTokenType() == JavaTokenType.SEMICOLON && eatSemicolon) { + builder.advanceLexer(); + } + else { + // special treatment (see DeclarationParserTest.testMultiLineUnclosed()) + if (!builder.eof() && shouldRollback) { + final CharSequence text = builder.getOriginalText(); + final int spaceEnd = builder.getCurrentOffset(); + final int spaceStart = CharArrayUtil.shiftBackward(text, spaceEnd-1, WHITESPACES); + final int lineStart = CharArrayUtil.shiftBackwardUntil(text, spaceEnd, LINE_ENDS); + + if (declarationStart < lineStart && lineStart < spaceStart) { + final int newBufferEnd = CharArrayUtil.shiftForward(text, lineStart, WHITESPACES); + declaration.rollbackTo(); + return parse(stoppingBuilder(builder, newBufferEnd), context); + } } - else { - // special treatment (see DeclarationParserTest.testMultiLineUnclosed()) - if (!builder.eof() && shouldRollback) { - final CharSequence text = builder.getOriginalText(); - final int spaceEnd = builder.getCurrentOffset(); - final int spaceStart = CharArrayUtil.shiftBackward(text, spaceEnd-1, WHITESPACES); - final int lineStart = CharArrayUtil.shiftBackwardUntil(text, spaceEnd, LINE_ENDS); - if (declarationStart < lineStart && lineStart < spaceStart) { - final int newBufferEnd = CharArrayUtil.shiftForward(text, lineStart, WHITESPACES); - declaration.rollbackTo(); - return parse(stoppingBuilder(builder, newBufferEnd), context); - } - } - - if (!unclosed) { - error(builder, JavaErrorMessages.message("expected.semicolon")); - } + if (!unclosed) { + error(builder, JavaErrorMessages.message("expected.semicolon")); } } diff --git a/java/java-impl/src/com/intellij/psi/controlFlow/ControlFlowAnalyzer.java b/java/java-impl/src/com/intellij/psi/controlFlow/ControlFlowAnalyzer.java index a7e726fae882..553515046fdf 100644 --- a/java/java-impl/src/com/intellij/psi/controlFlow/ControlFlowAnalyzer.java +++ b/java/java-impl/src/com/intellij/psi/controlFlow/ControlFlowAnalyzer.java @@ -1166,30 +1166,15 @@ class ControlFlowAnalyzer extends JavaJspElementVisitor { public void visitResourceList(final PsiResourceList resourceList) { startElement(resourceList); - final List resources = resourceList.getResources(); - for (PsiResource resource : resources) { + final List resources = resourceList.getResourceVariables(); + for (PsiResourceVariable resource : resources) { ProgressManager.checkCanceled(); - resource.accept(this); + processVariable(resource); } finishElement(resourceList); } - @Override - public void visitResource(final PsiResource resource) { - startElement(resource); - - final PsiElement resourceElement = resource.getResourceElement(); - if (resourceElement instanceof PsiLocalVariable) { - processVariable((PsiLocalVariable)resourceElement); - } - else if (resourceElement instanceof PsiExpression) { - resourceElement.accept(this); - } - - finishElement(resource); - } - @Override public void visitWhileStatement(PsiWhileStatement statement) { startElement(statement); diff --git a/java/java-impl/src/com/intellij/psi/controlFlow/DefUseUtil.java b/java/java-impl/src/com/intellij/psi/controlFlow/DefUseUtil.java index daba17413a5d..742863afe51a 100644 --- a/java/java-impl/src/com/intellij/psi/controlFlow/DefUseUtil.java +++ b/java/java-impl/src/com/intellij/psi/controlFlow/DefUseUtil.java @@ -230,11 +230,10 @@ public class DefUseUtil { if (!defsArmed[i]) { PsiElement context = PsiTreeUtil.getNonStrictParentOfType(flow.getElement(i), PsiStatement.class, PsiAssignmentExpression.class, - PsiPostfixExpression.class, PsiPrefixExpression.class, - PsiResource.class); + PsiPostfixExpression.class, PsiPrefixExpression.class); PsiVariable psiVariable = writeInstruction.variable; if (context != null && !(context instanceof PsiTryStatement)) { - if (isDeclaration(context) && psiVariable.getInitializer() == null) { + if (context instanceof PsiDeclarationStatement && psiVariable.getInitializer() == null) { if (!assignedVariables.contains(psiVariable)) { unusedDefs.add(new Info(psiVariable, context, false)); } @@ -250,11 +249,6 @@ public class DefUseUtil { return unusedDefs; } - private static boolean isDeclaration(final PsiElement context) { - return context instanceof PsiDeclarationStatement || - context instanceof PsiResource && ((PsiResource)context).getResourceElement() instanceof PsiLocalVariable; - } - @NotNull public static PsiElement[] getDefs(PsiCodeBlock body, final PsiVariable def, PsiElement ref) { try { diff --git a/java/java-impl/src/com/intellij/psi/impl/PsiImplUtil.java b/java/java-impl/src/com/intellij/psi/impl/PsiImplUtil.java index 44bbf950c6d1..85eea92a8563 100644 --- a/java/java-impl/src/com/intellij/psi/impl/PsiImplUtil.java +++ b/java/java-impl/src/com/intellij/psi/impl/PsiImplUtil.java @@ -198,12 +198,9 @@ public class PsiImplUtil { @NotNull final PsiScopeProcessor processor, @NotNull final ResolveState state, final PsiElement lastParent) { - final List resources = resourceList.getResources(); - for (PsiResource resource : resources) { - final PsiElement resourceElement = resource.getResourceElement(); - if (resourceElement instanceof PsiLocalVariable && - !resourceElement.equals(lastParent) && - !processor.execute(resourceElement, state)) return false; + final List resources = resourceList.getResourceVariables(); + for (PsiResourceVariable resource : resources) { + if (!resource.equals(lastParent) && !processor.execute(resource, state)) return false; } return true; diff --git a/java/java-impl/src/com/intellij/psi/impl/PsiJavaParserFacadeImpl.java b/java/java-impl/src/com/intellij/psi/impl/PsiJavaParserFacadeImpl.java index 49ec4a074d84..e8911819f860 100644 --- a/java/java-impl/src/com/intellij/psi/impl/PsiJavaParserFacadeImpl.java +++ b/java/java-impl/src/com/intellij/psi/impl/PsiJavaParserFacadeImpl.java @@ -259,13 +259,13 @@ public class PsiJavaParserFacadeImpl extends PsiParserFacadeImpl implements PsiJ @NotNull @Override - public PsiResource createResourceFromText(@NotNull final String text, final PsiElement context) throws IncorrectOperationException { + public PsiResourceVariable createResourceFromText(@NotNull final String text, final PsiElement context) throws IncorrectOperationException { final DummyHolder holder = DummyHolderFactory.createHolder(myManager, new JavaDummyElement(text, RESOURCE, false), context); final PsiElement element = SourceTreeToPsiMap.treeElementToPsi(holder.getTreeElement().getFirstChildNode()); - if (!(element instanceof PsiResource)) { + if (!(element instanceof PsiResourceVariable)) { throw new IncorrectOperationException("Incorrect resource \"" + text + "\"."); } - return (PsiResource)element; + return (PsiResourceVariable)element; } @NotNull diff --git a/java/java-impl/src/com/intellij/psi/impl/source/PsiModifierListImpl.java b/java/java-impl/src/com/intellij/psi/impl/source/PsiModifierListImpl.java index e2329c6d3578..2152c847a2e9 100644 --- a/java/java-impl/src/com/intellij/psi/impl/source/PsiModifierListImpl.java +++ b/java/java-impl/src/com/intellij/psi/impl/source/PsiModifierListImpl.java @@ -177,9 +177,8 @@ public class PsiModifierListImpl extends JavaStubPsiElement else if (parent instanceof PsiParameter) { if (type == JavaTokenType.FINAL_KEYWORD && ((PsiParameter)parent).getType() instanceof PsiDisjunctionType) return true; } - else if (parent instanceof PsiLocalVariable) { - PsiElement grandParent = parent.getParent(); - if (type == JavaTokenType.FINAL_KEYWORD && grandParent instanceof PsiResource) return true; + else if (parent instanceof PsiResourceVariable) { + if (type == JavaTokenType.FINAL_KEYWORD) return true; } if (type == null) { // package local diff --git a/java/java-impl/src/com/intellij/psi/impl/source/tree/JavaElementType.java b/java/java-impl/src/com/intellij/psi/impl/source/tree/JavaElementType.java index 593bb11d77c3..3a6026e33880 100644 --- a/java/java-impl/src/com/intellij/psi/impl/source/tree/JavaElementType.java +++ b/java/java-impl/src/com/intellij/psi/impl/source/tree/JavaElementType.java @@ -128,7 +128,7 @@ public interface JavaElementType { IElementType SYNCHRONIZED_STATEMENT = new JavaCompositeElementType("SYNCHRONIZED_STATEMENT", PsiSynchronizedStatementImpl.class); IElementType TRY_STATEMENT = new JavaCompositeElementType("TRY_STATEMENT", PsiTryStatementImpl.class); IElementType RESOURCE_LIST = new JavaCompositeElementType("RESOURCE_LIST", PsiResourceListImpl.class); - IElementType RESOURCE = new JavaCompositeElementType("RESOURCE", PsiResourceImpl.class); + IElementType RESOURCE_VARIABLE = new JavaCompositeElementType("RESOURCE_VARIABLE", PsiResourceVariableImpl.class); IElementType CATCH_SECTION = new JavaCompositeElementType("CATCH_SECTION", PsiCatchSectionImpl.class); IElementType LABELED_STATEMENT = new JavaCompositeElementType("LABELED_STATEMENT", PsiLabeledStatementImpl.class); IElementType ASSERT_STATEMENT = new JavaCompositeElementType("ASSERT_STATEMENT", PsiAssertStatementImpl.class); diff --git a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiLocalVariableImpl.java b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiLocalVariableImpl.java index ad809cdf9ad3..7ac00396e348 100644 --- a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiLocalVariableImpl.java +++ b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiLocalVariableImpl.java @@ -49,13 +49,17 @@ import org.jetbrains.annotations.NotNull; import javax.swing.*; import java.util.Set; -public class PsiLocalVariableImpl extends CompositePsiElement implements PsiScopedLocalVariable, PsiVariableEx, Constants { +public class PsiLocalVariableImpl extends CompositePsiElement implements PsiLocalVariable, PsiVariableEx, Constants { private static final Logger LOG = Logger.getInstance("#com.intellij.psi.impl.source.tree.java.PsiLocalVariableImpl"); private volatile String myCachedName = null; public PsiLocalVariableImpl() { - super(LOCAL_VARIABLE); + this(LOCAL_VARIABLE); + } + + protected PsiLocalVariableImpl(final IElementType type) { + super(type); } public void clearCaches() { @@ -279,21 +283,6 @@ public class PsiLocalVariableImpl extends CompositePsiElement implements PsiScop return "PsiLocalVariable:" + getName(); } - @NotNull - public PsiElement[] getDeclarationScope() { - final PsiElement parentElement = getParent(); - if (parentElement instanceof PsiDeclarationStatement) { - return new PsiElement[]{parentElement.getParent()}; - } - else if (parentElement instanceof PsiResource) { - final PsiResourceList resourceList = (PsiResourceList)parentElement.getParent(); - final PsiTryStatement tryStatement = (PsiTryStatement)resourceList.getParent(); - final PsiCodeBlock tryBlock = tryStatement.getTryBlock(); - return tryBlock != null ? new PsiElement[]{resourceList, tryBlock} : new PsiElement[]{resourceList}; - } - return new PsiElement[]{parentElement.getParent()}; - } - @NotNull public SearchScope getUseScope() { if (JspPsiUtil.isInJspFile(this)) { @@ -321,8 +310,8 @@ public class PsiLocalVariableImpl extends CompositePsiElement implements PsiScop } final PsiElement parentElement = getParent(); - if (parentElement instanceof PsiDeclarationStatement || parentElement instanceof PsiResource) { - return new LocalSearchScope(getDeclarationScope()); + if (parentElement instanceof PsiDeclarationStatement) { + return new LocalSearchScope(parentElement.getParent()); } else { return getManager().getFileManager().getUseScope(this); diff --git a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceImpl.java b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceImpl.java deleted file mode 100644 index 6a09eefdfece..000000000000 --- a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceImpl.java +++ /dev/null @@ -1,74 +0,0 @@ -/* - * Copyright 2000-2011 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 com.intellij.psi.impl.source.tree.java; - -import com.intellij.openapi.diagnostic.LogUtil; -import com.intellij.openapi.diagnostic.Logger; -import com.intellij.psi.*; -import com.intellij.psi.impl.source.tree.CompositePsiElement; -import com.intellij.psi.impl.source.tree.JavaElementType; -import org.jetbrains.annotations.NotNull; - -public class PsiResourceImpl extends CompositePsiElement implements PsiResource { - private static final Logger LOG = Logger.getInstance("#com.intellij.psi.impl.source.tree.java.PsiResourceImpl"); - - public PsiResourceImpl() { - super(JavaElementType.RESOURCE); - } - - @NotNull - @Override - public PsiElement getResourceElement() { - final PsiElement element = getFirstChild(); - assert element != null : this; - return element; - } - - @Override - public PsiType getType() { - final PsiElement element = getResourceElement(); - if (element instanceof PsiLocalVariable) { - return ((PsiLocalVariable)element).getType(); - } - else if (element instanceof PsiExpression) { - return ((PsiExpression)element).getType(); - } - LOG.error("Unexpected resource type: " + LogUtil.objectAndClass(element)); - return null; - } - - @Override - public void accept(@NotNull final PsiElementVisitor visitor) { - if (visitor instanceof JavaElementVisitor) { - ((JavaElementVisitor)visitor).visitResource(this); - } - else { - visitor.visitElement(this); - } - } - - public String getName() { - final PsiElement element = getFirstChild(); - if (element instanceof PsiLocalVariable) return ((PsiLocalVariable)element).getName(); - if (element instanceof PsiAssignmentExpression) return ((PsiAssignmentExpression)element).getLExpression().toString(); - return ""; - } - - @Override - public String toString() { - return "PsiResource:" + getName(); - } -} diff --git a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceListImpl.java b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceListImpl.java index 0ecec5626043..a6b67409cab1 100644 --- a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceListImpl.java +++ b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceListImpl.java @@ -32,8 +32,8 @@ public class PsiResourceListImpl extends CompositePsiElement implements PsiResou @NotNull @Override - public List getResources() { - return PsiTreeUtil.getChildrenOfTypeAsList(this, PsiResource.class); + public List getResourceVariables() { + return PsiTreeUtil.getChildrenOfTypeAsList(this, PsiResourceVariable.class); } @Override diff --git a/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceVariableImpl.java b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceVariableImpl.java new file mode 100644 index 000000000000..4df67b7ced2a --- /dev/null +++ b/java/java-impl/src/com/intellij/psi/impl/source/tree/java/PsiResourceVariableImpl.java @@ -0,0 +1,70 @@ +/* + * Copyright 2000-2011 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 com.intellij.psi.impl.source.tree.java; + +import com.intellij.psi.*; +import com.intellij.psi.impl.source.tree.JavaElementType; +import com.intellij.psi.search.LocalSearchScope; +import com.intellij.psi.search.SearchScope; +import com.intellij.psi.util.PsiTreeUtil; +import org.jetbrains.annotations.NotNull; + +public class PsiResourceVariableImpl extends PsiLocalVariableImpl implements PsiResourceVariable { + public PsiResourceVariableImpl() { + super(JavaElementType.RESOURCE_VARIABLE); + } + + @NotNull + @Override + public PsiElement[] getDeclarationScope() { + final PsiResourceList resourceList = (PsiResourceList)getParent(); + final PsiTryStatement tryStatement = (PsiTryStatement)resourceList.getParent(); + final PsiCodeBlock tryBlock = tryStatement.getTryBlock(); + return tryBlock != null ? new PsiElement[]{resourceList, tryBlock} : new PsiElement[]{resourceList}; + } + + @NotNull + @Override + public PsiTypeElement getTypeElement() { + return PsiTreeUtil.getRequiredChildOfType(this, PsiTypeElement.class); + } + + @Override + public PsiModifierList getModifierList() { + return PsiTreeUtil.getChildOfType(this, PsiModifierList.class); + } + + @Override + public void accept(@NotNull final PsiElementVisitor visitor) { + if (visitor instanceof JavaElementVisitor) { + ((JavaElementVisitor)visitor).visitResourceVariable(this); + } + else { + visitor.visitElement(this); + } + } + + @NotNull + @Override + public SearchScope getUseScope() { + return new LocalSearchScope(getDeclarationScope()); + } + + @Override + public String toString() { + return "PsiResourceVariable:" + getName(); + } +} diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResources.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResources.java index fa8f950ef4b1..63a5b7b9e619 100644 --- a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResources.java +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResources.java @@ -14,24 +14,22 @@ class C { try (MyResource r = new MyResource()) { r.doSomething(); } catch (E1 | E2 | E3 ignore) { } - try (new MyResource()) { } + try (MyResource r = new MyResource()) { } catch (E1 | E3 ignore) { } - MyResource r; - - try (r = new MyResource()) { } + try (MyResource r = new MyResource()) { } catch (E1 e) { } - try (r = new MyResource()) { } + try (MyResource r = new MyResource()) { } catch (E3 e) { } - try (r = new MyResource()) { } + try (MyResource r = new MyResource()) { } } void m2() throws Exception { try (Object r = new MyResource()) { } - try ("resource") { } + try (AutoCloseable r = "resource") { } } void m3(int p) throws Exception { @@ -56,7 +54,7 @@ class C { MyResource r = null; try (MyResource r = new MyResource()) { } - try (r = new MyResource()) { } + try (MyResource rr = r) { } try (MyResource p = new MyResource()) { } new Runnable() { diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResourcesWarn.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResourcesWarn.java index 68b4fb4b4925..2cf0fe3f0c2d 100644 --- a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResourcesWarn.java +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/TryWithResourcesWarn.java @@ -6,35 +6,28 @@ class C { } void m1() throws Exception { - MyResource r1; - try (r1 = new MyResource()) { + try (MyResource r1 = new MyResource()) { System.out.println(r1); } - try (MyResource r2 = new MyResource()) { - System.out.println(r2); - } - - MyResource r3 = new MyResource(); - try (MyResource r = r3) { + MyResource r2 = new MyResource(); + try (MyResource r = r2) { System.out.println(r); + System.out.println(r2); } } void m2() throws Exception { - MyResource r1 = null; - try (r1 = new MyResource()) { - System.out.println(r1); - } + // todo: test in IG + //MyResource < warning descr="Local variable 'r1' is redundant">r1 = null; + //try (MyResource r = r1) { + // System.out.println(r); + //} - MyResource r2 = null; - System.out.println(r2); - try (r2 = new MyResource()) { } + try (MyResource r2 = new MyResource()) { } - try (MyResource r3 = new MyResource()) { } - - MyResource r4; - try (MyResource r = r4) { + MyResource r3; + try (MyResource r = r3) { System.out.println(r); } } diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete10.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete10.txt index 2e113f719226..07461ff12a2d 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete10.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete10.txt @@ -3,6 +3,8 @@ PsiJavaFile:TryIncomplete10.java PsiKeyword:try('try') PsiResourceList:( PsiJavaToken:LPARENTH('(') + PsiErrorElement:Identifier or type expected + PsiErrorElement:')' expected PsiCodeBlock diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete11.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete11.txt index 11b2811b4174..fda6eb428b58 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete11.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete11.txt @@ -3,7 +3,7 @@ PsiJavaFile:TryIncomplete11.java PsiKeyword:try('try') PsiResourceList:() PsiJavaToken:LPARENTH('(') - PsiErrorElement:Resource definition expected + PsiErrorElement:Identifier or type expected PsiJavaToken:RPARENTH(')') PsiCodeBlock diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete12.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete12.txt index 78a125c530b4..f37c59d95818 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete12.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete12.txt @@ -6,8 +6,6 @@ PsiJavaFile:TryIncomplete12.java PsiErrorElement:Resource definition expected PsiJavaToken:SEMICOLON(';') - PsiErrorElement:Resource definition expected - PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete13.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete13.txt index 598f1ac3e5c0..b4301f60f0b6 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete13.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete13.txt @@ -5,9 +5,13 @@ PsiJavaFile:TryIncomplete13.java PsiJavaToken:LPARENTH('(') PsiModifierList:final PsiKeyword:final('final') - PsiErrorElement:Identifier or type expected + PsiErrorElement:Type expected PsiWhiteSpace(' ') + PsiTypeElement: + + PsiErrorElement:Identifier expected + PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete14.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete14.txt index 88a8aca925b2..97482c52ec46 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete14.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete14.txt @@ -3,8 +3,12 @@ PsiJavaFile:TryIncomplete14.java PsiKeyword:try('try') PsiResourceList:(int) PsiJavaToken:LPARENTH('(') - PsiErrorElement:Resource definition expected + PsiModifierList: + + PsiTypeElement:int PsiKeyword:int('int') + PsiErrorElement:Identifier expected + PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete15.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete15.txt index 5748458436f0..2da2c5a6c22a 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete15.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete15.txt @@ -3,19 +3,18 @@ PsiJavaFile:TryIncomplete15.java PsiKeyword:try('try') PsiResourceList:(R r) PsiJavaToken:LPARENTH('(') - PsiResource:r - PsiLocalVariable:r - PsiModifierList: - - PsiTypeElement:R - PsiJavaCodeReferenceElement:R - PsiIdentifier:R('R') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r('r') - PsiErrorElement:'=' expected - + PsiResourceVariable:r + PsiModifierList: + + PsiTypeElement:R + PsiJavaCodeReferenceElement:R + PsiIdentifier:R('R') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r('r') + PsiErrorElement:'=' expected + PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete16.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete16.txt index e04ca47331f8..837e354734f4 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete16.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete16.txt @@ -3,21 +3,20 @@ PsiJavaFile:TryIncomplete16.java PsiKeyword:try('try') PsiResourceList:(R r =) PsiJavaToken:LPARENTH('(') - PsiResource:r - PsiLocalVariable:r - PsiModifierList: - - PsiTypeElement:R - PsiJavaCodeReferenceElement:R - PsiIdentifier:R('R') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r('r') - PsiWhiteSpace(' ') - PsiJavaToken:EQ('=') - PsiErrorElement:Expression expected - + PsiResourceVariable:r + PsiModifierList: + + PsiTypeElement:R + PsiJavaCodeReferenceElement:R + PsiIdentifier:R('R') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r('r') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiErrorElement:Expression expected + PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete17.txt b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete17.txt index e4f111fb50c8..cf19d8c861dc 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete17.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryIncomplete17.txt @@ -1,27 +1,27 @@ PsiJavaFile:TryIncomplete17.java PsiTryStatement PsiKeyword:try('try') - PsiResourceList:(R r = 0;) + PsiResourceList:(R r = 0;;) PsiJavaToken:LPARENTH('(') - PsiResource:r - PsiLocalVariable:r - PsiModifierList: - - PsiTypeElement:R - PsiJavaCodeReferenceElement:R - PsiIdentifier:R('R') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r('r') - PsiWhiteSpace(' ') - PsiJavaToken:EQ('=') - PsiWhiteSpace(' ') - PsiLiteralExpression:0 - PsiJavaToken:INTEGER_LITERAL('0') + PsiResourceVariable:r + PsiModifierList: + + PsiTypeElement:R + PsiJavaCodeReferenceElement:R + PsiIdentifier:R('R') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r('r') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiWhiteSpace(' ') + PsiLiteralExpression:0 + PsiJavaToken:INTEGER_LITERAL('0') PsiJavaToken:SEMICOLON(';') - PsiErrorElement:Identifier or type expected + PsiErrorElement:Resource definition expected + PsiJavaToken:SEMICOLON(';') PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryNormal4.txt b/java/java-tests/testData/psi/parser-partial/statements/TryNormal4.txt index c3bec38b2bf4..35a8f5f03eec 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryNormal4.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryNormal4.txt @@ -3,22 +3,21 @@ PsiJavaFile:TryNormal4.java PsiKeyword:try('try') PsiResourceList:(R r = 0) PsiJavaToken:LPARENTH('(') - PsiResource:r - PsiLocalVariable:r - PsiModifierList: - - PsiTypeElement:R - PsiJavaCodeReferenceElement:R - PsiIdentifier:R('R') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r('r') - PsiWhiteSpace(' ') - PsiJavaToken:EQ('=') - PsiWhiteSpace(' ') - PsiLiteralExpression:0 - PsiJavaToken:INTEGER_LITERAL('0') + PsiResourceVariable:r + PsiModifierList: + + PsiTypeElement:R + PsiJavaCodeReferenceElement:R + PsiIdentifier:R('R') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r('r') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiWhiteSpace(' ') + PsiLiteralExpression:0 + PsiJavaToken:INTEGER_LITERAL('0') PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryNormal5.txt b/java/java-tests/testData/psi/parser-partial/statements/TryNormal5.txt index b69bed12f700..7a09f71bba3e 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryNormal5.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryNormal5.txt @@ -3,40 +3,38 @@ PsiJavaFile:TryNormal5.java PsiKeyword:try('try') PsiResourceList:(R1 r1 = 1; R2 r2 = 2) PsiJavaToken:LPARENTH('(') - PsiResource:r1 - PsiLocalVariable:r1 - PsiModifierList: - - PsiTypeElement:R1 - PsiJavaCodeReferenceElement:R1 - PsiIdentifier:R1('R1') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r1('r1') - PsiWhiteSpace(' ') - PsiJavaToken:EQ('=') - PsiWhiteSpace(' ') - PsiLiteralExpression:1 - PsiJavaToken:INTEGER_LITERAL('1') + PsiResourceVariable:r1 + PsiModifierList: + + PsiTypeElement:R1 + PsiJavaCodeReferenceElement:R1 + PsiIdentifier:R1('R1') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r1('r1') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiWhiteSpace(' ') + PsiLiteralExpression:1 + PsiJavaToken:INTEGER_LITERAL('1') PsiJavaToken:SEMICOLON(';') PsiWhiteSpace(' ') - PsiResource:r2 - PsiLocalVariable:r2 - PsiModifierList: - - PsiTypeElement:R2 - PsiJavaCodeReferenceElement:R2 - PsiIdentifier:R2('R2') - PsiReferenceParameterList - - PsiWhiteSpace(' ') - PsiIdentifier:r2('r2') - PsiWhiteSpace(' ') - PsiJavaToken:EQ('=') - PsiWhiteSpace(' ') - PsiLiteralExpression:2 - PsiJavaToken:INTEGER_LITERAL('2') + PsiResourceVariable:r2 + PsiModifierList: + + PsiTypeElement:R2 + PsiJavaCodeReferenceElement:R2 + PsiIdentifier:R2('R2') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r2('r2') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiWhiteSpace(' ') + PsiLiteralExpression:2 + PsiJavaToken:INTEGER_LITERAL('2') PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryNormal6.txt b/java/java-tests/testData/psi/parser-partial/statements/TryNormal6.txt index bf1b0ed88fd3..272652e46932 100644 --- a/java/java-tests/testData/psi/parser-partial/statements/TryNormal6.txt +++ b/java/java-tests/testData/psi/parser-partial/statements/TryNormal6.txt @@ -1,13 +1,24 @@ PsiJavaFile:TryNormal6.java PsiTryStatement PsiKeyword:try('try') - PsiResourceList:(r) + PsiResourceList:(R r = 0;) PsiJavaToken:LPARENTH('(') - PsiResource: - PsiReferenceExpression:r - PsiReferenceParameterList - - PsiIdentifier:r('r') + PsiResourceVariable:r + PsiModifierList: + + PsiTypeElement:R + PsiJavaCodeReferenceElement:R + PsiIdentifier:R('R') + PsiReferenceParameterList + + PsiWhiteSpace(' ') + PsiIdentifier:r('r') + PsiWhiteSpace(' ') + PsiJavaToken:EQ('=') + PsiWhiteSpace(' ') + PsiLiteralExpression:0 + PsiJavaToken:INTEGER_LITERAL('0') + PsiJavaToken:SEMICOLON(';') PsiJavaToken:RPARENTH(')') PsiCodeBlock PsiJavaToken:LBRACE('{') diff --git a/java/java-tests/testData/psi/parser-partial/statements/TryNormal7.txt b/java/java-tests/testData/psi/parser-partial/statements/TryNormal7.txt deleted file mode 100644 index 1299595c7a9b..000000000000 --- a/java/java-tests/testData/psi/parser-partial/statements/TryNormal7.txt +++ /dev/null @@ -1,19 +0,0 @@ -PsiJavaFile:TryNormal7.java - PsiTryStatement - PsiKeyword:try('try') - PsiResourceList:(r; null) - PsiJavaToken:LPARENTH('(') - PsiResource: - PsiReferenceExpression:r - PsiReferenceParameterList - - PsiIdentifier:r('r') - PsiJavaToken:SEMICOLON(';') - PsiWhiteSpace(' ') - PsiResource: - PsiLiteralExpression:null - PsiJavaToken:NULL_KEYWORD('null') - PsiJavaToken:RPARENTH(')') - PsiCodeBlock - PsiJavaToken:LBRACE('{') - PsiJavaToken:RBRACE('}') \ No newline at end of file diff --git a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/LightAdvHighlightingJdk7Test.java b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/LightAdvHighlightingJdk7Test.java index 83a619d5559d..5982a56f7a16 100644 --- a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/LightAdvHighlightingJdk7Test.java +++ b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/LightAdvHighlightingJdk7Test.java @@ -32,7 +32,7 @@ public class LightAdvHighlightingJdk7Test extends LightDaemonAnalyzerTestCase { @Override protected LocalInspectionTool[] configureLocalInspectionTools() { - return new LocalInspectionTool[]{new UnusedSymbolLocalInspection(), new UncheckedWarningLocalInspection(), new DefUseInspection()}; + return new LocalInspectionTool[]{new UnusedSymbolLocalInspection(), new UncheckedWarningLocalInspection()}; } public void testDuplicateAnnotations() throws Exception { @@ -194,6 +194,7 @@ public class LightAdvHighlightingJdk7Test extends LightDaemonAnalyzerTestCase { } public void testTryWithResourcesWarn() throws Exception { + enableInspectionTool(new DefUseInspection()); doTest(true, false); } diff --git a/java/java-tests/testSrc/com/intellij/lang/java/parser/partial/StatementParserTest.java b/java/java-tests/testSrc/com/intellij/lang/java/parser/partial/StatementParserTest.java index df12da3f6c62..118d33e54e96 100644 --- a/java/java-tests/testSrc/com/intellij/lang/java/parser/partial/StatementParserTest.java +++ b/java/java-tests/testSrc/com/intellij/lang/java/parser/partial/StatementParserTest.java @@ -122,8 +122,7 @@ public class StatementParserTest extends JavaParsingTestCase { public void testTryNormal3() { doParserTestJDK7("try{}catch(A|B e){}"); } public void testTryNormal4() { doParserTestJDK7("try(R r = 0){}"); } public void testTryNormal5() { doParserTestJDK7("try(R1 r1 = 1; R2 r2 = 2){}"); } - public void testTryNormal6() { doParserTestJDK7("try(r){}"); } - public void testTryNormal7() { doParserTestJDK7("try(r; null){}"); } + public void testTryNormal6() { doParserTestJDK7("try(R r = 0;){}"); } public void testTryIncomplete0() { doParserTest("try"); } public void testTryIncomplete1() { doParserTest("try{}"); } public void testTryIncomplete2() { doParserTest("try{}catch"); } @@ -141,7 +140,7 @@ public class StatementParserTest extends JavaParsingTestCase { public void testTryIncomplete14() { doParserTestJDK7("try(int){}"); } public void testTryIncomplete15() { doParserTestJDK7("try(R r){}"); } public void testTryIncomplete16() { doParserTestJDK7("try(R r =){}"); } - public void testTryIncomplete17() { doParserTestJDK7("try(R r = 0;){}"); } + public void testTryIncomplete17() { doParserTestJDK7("try(R r = 0;;){}"); } public void testWhileNormal() { doParserTest("while (true) foo();"); } public void testWhileIncomplete0() { doParserTest("while"); } diff --git a/java/openapi/src/com/intellij/psi/JavaElementVisitor.java b/java/openapi/src/com/intellij/psi/JavaElementVisitor.java index c8162c6004b3..772a1e7963b3 100644 --- a/java/openapi/src/com/intellij/psi/JavaElementVisitor.java +++ b/java/openapi/src/com/intellij/psi/JavaElementVisitor.java @@ -300,8 +300,8 @@ public abstract class JavaElementVisitor extends PsiElementVisitor { visitElement(resourceList); } - public void visitResource(PsiResource resource) { - visitElement(resource); + public void visitResourceVariable(PsiResourceVariable resourceVariable) { + visitLocalVariable(resourceVariable); } public void visitTypeElement(PsiTypeElement type) { diff --git a/java/openapi/src/com/intellij/psi/PsiJavaParserFacade.java b/java/openapi/src/com/intellij/psi/PsiJavaParserFacade.java index 6e59d5430e38..332f2f2928f2 100644 --- a/java/openapi/src/com/intellij/psi/PsiJavaParserFacade.java +++ b/java/openapi/src/com/intellij/psi/PsiJavaParserFacade.java @@ -125,7 +125,7 @@ public interface PsiJavaParserFacade extends PsiParserFacade { * @throws com.intellij.util.IncorrectOperationException if the text is not a valid resource definition. */ @NotNull - PsiResource createResourceFromText(@NotNull final String text, final PsiElement context) throws IncorrectOperationException; + PsiResourceVariable createResourceFromText(@NotNull final String text, final PsiElement context) throws IncorrectOperationException; /** * Creates a Java type from the specified text. diff --git a/java/openapi/src/com/intellij/psi/PsiResource.java b/java/openapi/src/com/intellij/psi/PsiResource.java deleted file mode 100644 index e53289079c86..000000000000 --- a/java/openapi/src/com/intellij/psi/PsiResource.java +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Copyright 2000-2011 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 com.intellij.psi; - -import org.jetbrains.annotations.NotNull; -import org.jetbrains.annotations.Nullable; - -/** - * Represents a resource list of try-with-resources statement (automatic resource management) introduced in JDK 7. - * - * @see PsiResourceList#getResources() - * @since 10.5. - */ -public interface PsiResource extends PsiElement { - /** - * Returns main element of the resource. - * It may be PsiLocalVariable, PsiAssignmentExpression, or other instance of PsiExpression. - * - * @return resource element. - */ - @NotNull - PsiElement getResourceElement(); - - @Nullable - PsiType getType(); -} diff --git a/java/openapi/src/com/intellij/psi/PsiResourceList.java b/java/openapi/src/com/intellij/psi/PsiResourceList.java index c954ae7e79bd..831151b15cc0 100644 --- a/java/openapi/src/com/intellij/psi/PsiResourceList.java +++ b/java/openapi/src/com/intellij/psi/PsiResourceList.java @@ -27,5 +27,5 @@ import java.util.List; */ public interface PsiResourceList extends PsiElement { @NotNull - List getResources(); + List getResourceVariables(); } diff --git a/java/openapi/src/com/intellij/psi/PsiScopedLocalVariable.java b/java/openapi/src/com/intellij/psi/PsiResourceVariable.java similarity index 73% rename from java/openapi/src/com/intellij/psi/PsiScopedLocalVariable.java rename to java/openapi/src/com/intellij/psi/PsiResourceVariable.java index b6f74359b683..113d69c321e2 100644 --- a/java/openapi/src/com/intellij/psi/PsiScopedLocalVariable.java +++ b/java/openapi/src/com/intellij/psi/PsiResourceVariable.java @@ -17,12 +17,13 @@ package com.intellij.psi; import org.jetbrains.annotations.NotNull; -public interface PsiScopedLocalVariable extends PsiLocalVariable { - /** - * Returns the element or elements (method, "for" statement or try block) in which the variable is declared. - * - * @return the declaration scope for the variable. - */ +/** + * Represents a resource variable of try-with-resources statement (automatic resource management) introduced in JDK 7. + * + * @see PsiResourceList#getResourceVariables() + * @since 10.5. + */ +public interface PsiResourceVariable extends PsiLocalVariable { @NotNull PsiElement[] getDeclarationScope(); }