diff options
Diffstat (limited to 'org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal')
3 files changed, 61 insertions, 27 deletions
diff --git a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/complete/CompletionParser.java b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/complete/CompletionParser.java index 38eaad8ce3..3ae6696750 100644 --- a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/complete/CompletionParser.java +++ b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/complete/CompletionParser.java @@ -7,6 +7,10 @@ * https://www.eclipse.org/legal/epl-2.0/ * * SPDX-License-Identifier: EPL-2.0 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. * * Contributors: * IBM Corporation - initial API and implementation @@ -99,6 +103,7 @@ public class CompletionParser extends AssistParser { protected static final int K_AFTER_NAME_IN_PROVIDES_STATEMENT = COMPLETION_PARSER + 49; protected static final int K_AFTER_WITH_IN_PROVIDES_STATEMENT = COMPLETION_PARSER + 50; protected static final int K_INSIDE_OPENS_STATEMENT = COMPLETION_PARSER + 51; + protected static final int K_YIELD_KEYWORD = COMPLETION_PARSER + 52; public final static char[] FAKE_TYPE_NAME = new char[]{' '}; @@ -1675,6 +1680,14 @@ private boolean checkInstanceofKeyword() { } return false; } +private boolean checkYieldKeyword() { + // Clients to ensure that we are already inside a method + char[] id = this.scanner.getCurrentIdentifierSource(); + if(id.length > 0 && CharOperation.prefixEquals(id, Keywords.YIELD)) { + return true; + } + return false; +} /** * Checks if the completion is inside a method invocation or a constructor invocation. * Returns whether we found a completion node. @@ -3798,6 +3811,12 @@ protected void consumePushPosition() { } } @Override +protected void consumeSwitchLabeledBlock() { + popUntilElement(K_SWITCH_LABEL); + popElement(K_SWITCH_LABEL); + concatNodeLists(); +} +@Override protected void consumeToken(int token) { if(this.isFirst) { super.consumeToken(token); @@ -3826,6 +3845,10 @@ protected void consumeToken(int token) { break; case TokenNameLBRACE: popElement(K_BETWEEN_NEW_AND_LEFT_BRACKET); + if(topKnownElementKind(COMPLETION_OR_ASSIST_PARSER) == K_SWITCH_LABEL + && previous == TokenNameARROW) { + pushOnElementStack(K_SWITCH_EXPRESSION_DELIMITTER); + } break; case TokenNameLBRACKET: if(topKnownElementKind(COMPLETION_OR_ASSIST_PARSER) == K_BETWEEN_NEW_AND_LEFT_BRACKET) { @@ -3916,6 +3939,16 @@ protected void consumeToken(int token) { case TokenNameIdentifier: if (this.inReferenceExpression) break; + if (this.scanner.previewEnabled && isInsideSwitch() && checkYieldKeyword()) { + pushOnElementStack(K_YIELD_KEYWORD); + // Take the short cut here. + // Instead of injecting the TokenNameRestrictedIdentifierYield, totally ignore it + // and let completion take it course. We will not be constructing the + // YieldStatement and thus not producing accurate completion, but completion doesn't have + // enough information anyway about the LHS anyway. + token = this.currentToken = this.getNextToken(); + super.consumeToken(this.currentToken); + } if (previous == TokenNameDOT) { // e.g. foo().[fred]() if (this.invocationType != SUPER_RECEIVER // e.g. not super.[fred]() && this.invocationType != NAME_RECEIVER // e.g. not bar.[fred]() @@ -4321,6 +4354,7 @@ protected void consumeToken(int token) { pushOnElementStack(K_BETWEEN_FOR_AND_RIGHT_PAREN, this.bracketDepth); break; case TokenNameswitch: + popElement(K_LOCAL_INITIALIZER_DELIMITER); pushOnElementStack(K_BETWEEN_SWITCH_AND_RIGHT_PAREN, this.bracketDepth); break; case TokenNamesynchronized: @@ -4864,7 +4898,8 @@ public NameReference createSingleAssistNameReference(char[] assistName, long pos // https://bugs.eclipse.org/bugs/show_bug.cgi?id=269493: Keywords are not proposed in a for // loop without block. Completion while at K_CONTROL_STATEMENT_DELIMITER case needs to handled // similar to the K_BLOCK_DELIMITER with minor differences. - if(kind == K_BLOCK_DELIMITER || kind == K_CONTROL_STATEMENT_DELIMITER || kind == K_LAMBDA_EXPRESSION_DELIMITER) { + if(kind == K_BLOCK_DELIMITER || kind == K_CONTROL_STATEMENT_DELIMITER || kind == K_LAMBDA_EXPRESSION_DELIMITER + || kind == K_SWITCH_EXPRESSION_DELIMITTER) { if(this.canBeExplicitConstructor == YES) { canBeExplicitConstructorCall = true; } @@ -4906,6 +4941,9 @@ public NameReference createSingleAssistNameReference(char[] assistName, long pos if(isInsideBreakable()) { keywords[count++]= Keywords.BREAK; } + if(isInsideSwitch()) { + keywords[count++]= Keywords.YIELD; + } } else if (kind == K_BETWEEN_FOR_AND_RIGHT_PAREN) { if (this.options.complianceLevel >= ClassFileConstants.JDK10) { keywords[count++]= Keywords.VAR; @@ -4920,13 +4958,16 @@ public NameReference createSingleAssistNameReference(char[] assistName, long pos keywords[count++]= Keywords.TRUE; keywords[count++]= Keywords.FALSE; keywords[count++]= Keywords.NULL; - + if (kind == K_YIELD_KEYWORD) { + keywords[count++]= Keywords.YIELD; + } if(kind == K_SWITCH_LABEL) { if(topKnownElementInfo(COMPLETION_OR_ASSIST_PARSER) != DEFAULT) { keywords[count++]= Keywords.DEFAULT; } keywords[count++]= Keywords.BREAK; keywords[count++]= Keywords.CASE; + keywords[count++]= Keywords.YIELD; if (this.options.complianceLevel >= ClassFileConstants.JDK1_4) { keywords[count++]= Keywords.ASSERT; } @@ -5124,9 +5165,7 @@ protected NameReference getUnspecifiedReference(boolean rejectTypeAnnotations) { @Override protected void consumePostfixExpression() { // PostfixExpression ::= Name - if(this.topKnownElementKind(COMPLETION_OR_ASSIST_PARSER) == K_INSIDE_BREAK_STATEMENT) { - // Do nothing, just let checkLabelStatement() do the job - } else { + if (topKnownElementKind(COMPLETION_OR_ASSIST_PARSER) != K_YIELD_KEYWORD) { super.consumePostfixExpression(); } } @@ -5231,24 +5270,11 @@ protected boolean isInsideAnnotation() { return false; } -protected boolean isIndirectlyInsideBlock(){ - int i = this.elementPtr; - while(i > -1) { - if(this.elementKindStack[i] == K_BLOCK_DELIMITER) - return true; - i--; - } - return false; -} - -protected boolean isInsideBlock(){ +protected boolean isInsideSwitch(){ int i = this.elementPtr; while(i > -1) { switch (this.elementKindStack[i]) { - case K_TYPE_DELIMITER : return false; - case K_METHOD_DELIMITER : return false; - case K_FIELD_INITIALIZER_DELIMITER : return false; - case K_BLOCK_DELIMITER : return true; + case K_SWITCH_LABEL : return true; } i--; } diff --git a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java index 99804638db..fa1531dedb 100644 --- a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java +++ b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java @@ -8,6 +8,10 @@ * * SPDX-License-Identifier: EPL-2.0 * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * * Contributors: * IBM Corporation - initial API and implementation *******************************************************************************/ @@ -104,6 +108,7 @@ public abstract class AssistParser extends Parser { protected static final int K_ENUM_CONSTANT_DELIMITER = ASSIST_PARSER + 6; // whether we are inside a field initializer protected static final int K_LAMBDA_EXPRESSION_DELIMITER = ASSIST_PARSER + 7; // whether we are inside a lambda expression protected static final int K_MODULE_INFO_DELIMITER = ASSIST_PARSER + 8; // whether we are inside a module info declaration + protected static final int K_SWITCH_EXPRESSION_DELIMITTER = ASSIST_PARSER + 9; // whether we are inside a switch expression // selector constants protected static final int THIS_CONSTRUCTOR = -1; @@ -1281,11 +1286,8 @@ private void adjustBracket(int token) { break; } } -private boolean lastArrowAssociatedWithCase = false; @Override protected void consumeToken(int token) { - if (TokenNameARROW == token) - this.lastArrowAssociatedWithCase = this.caseFlagSet; // remember the arrow association before reset. super.consumeToken(token); if(this.isFirst) { @@ -1318,9 +1320,10 @@ protected void consumeToken(int token) { } break; case TokenNameLBRACE: - if (this.previousToken == TokenNameARROW && !this.lastArrowAssociatedWithCase) { + if (this.previousToken == TokenNameARROW) { popElement(K_LAMBDA_EXPRESSION_DELIMITER); - pushOnElementStack(K_LAMBDA_EXPRESSION_DELIMITER, BLOCK_BODY, this.previousObjectInfo); + if (topKnownElementKind(ASSIST_PARSER, 1) != K_SWITCH_EXPRESSION_DELIMITTER) + pushOnElementStack(K_LAMBDA_EXPRESSION_DELIMITER, BLOCK_BODY, this.previousObjectInfo); } break; } diff --git a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/Keywords.java b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/Keywords.java index 2fb6ab568b..ba10f2c3d8 100644 --- a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/Keywords.java +++ b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/Keywords.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2018 IBM Corporation and others. + * Copyright (c) 2000, 2019 IBM Corporation and others. * * This program and the accompanying materials * are made available under the terms of the Eclipse Public License 2.0 @@ -7,7 +7,11 @@ * https://www.eclipse.org/legal/epl-2.0/ * * SPDX-License-Identifier: EPL-2.0 - * + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * * Contributors: * IBM Corporation - initial API and implementation * Jesper Steen Møller - Contributions for @@ -22,6 +26,7 @@ public interface Keywords { char[] ASSERT = "assert".toCharArray(); //$NON-NLS-1$ char[] BREAK = "break".toCharArray(); //$NON-NLS-1$ char[] CASE = "case".toCharArray(); //$NON-NLS-1$ + char[] YIELD = "yield".toCharArray(); //$NON-NLS-1$ char[] CATCH = "catch".toCharArray(); //$NON-NLS-1$ char[] CLASS = "class".toCharArray(); //$NON-NLS-1$ char[] CONTINUE = "continue".toCharArray(); //$NON-NLS-1$ |