eclipse-jdt / eclipse-jdt/eclipse.jdt.core

Selection in switch in lambda violates a parser assertion

Open
#4,734 1 comment 0 reactions 1 assignee Claimed by @srikanth-sankaran View on GitHub
Dominant language
Java
Stars
237
Forks
195
Avg merge
1d 12h
Merged PRs (30d)
47

Description

Given:
```java
package test;

import java.util.function.Consumer;

public class Test {
public static final int ONE = 1;
Consumer c = i -> {
switch (i) {
case ONE: return;
}
};
}
```
Try to select the case constant `ONE` in a workbench with assertions enabled.

Result:
```
java.lang.AssertionError: Block positions should be consistent
at org.eclipse.jdt.internal.codeassist.impl.AssistParser.consumeBlock(AssistParser.java:697)
at org.eclipse.jdt.internal.codeassist.select.SelectionParser.consumeBlock(SelectionParser.java:1127)
at org.eclipse.jdt.internal.compiler.parser.Parser.consumeRule(Parser.java:7068)
at org.eclipse.jdt.internal.compiler.parser.Parser.parse(Parser.java:11731)
at org.eclipse.jdt.internal.compiler.parser.Parser.parse(Parser.java:12005)
at org.eclipse.jdt.internal.codeassist.select.SelectionParser.parse(SelectionParser.java:1873)
at org.eclipse.jdt.internal.compiler.parser.Parser.parse(Parser.java:11946)
at org.eclipse.jdt.internal.compiler.parser.Parser.dietParse(Parser.java:10333)
at org.eclipse.jdt.internal.codeassist.select.SelectionParser.dietParse(SelectionParser.java:1696)
at org.eclipse.jdt.internal.codeassist.SelectionEngine.select(SelectionEngine.java:934)
at org.eclipse.jdt.internal.core.Openable.codeSelect(Openable.java:171)
...
```

Preliminary analysis indicates that the `consumeOpenBlock()` of the switch statement is not matched by `consumeBlock()` as expected, by which we miss to pop an element from the snapshot stack.

Perhaps SelectionParser needs to override also `consumeSwitchBlock()` to perform the matching pop. Additionally, I didn't even observe `consumeSwitchBlock()` being called, perhaps because of this inconsistency in java.g:
```
SwitchBlock -> '{' SwitchBlockStatements '}'
SwitchBlock -> '{' SwitchLabels '}'
SwitchBlock ::= '{' SwitchBlockStatements SwitchLabels '}'
/.$putCase consumeSwitchBlock(true) ; $break ./
/:$readableName SwitchBlock:/
```
(Not putCase for the first two forms of SwitchBlock.)

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.