diff --git a/antlr5-maven-plugin/pom.xml b/antlr5-maven-plugin/pom.xml index 1341fb59e..90abbc6f8 100644 --- a/antlr5-maven-plugin/pom.xml +++ b/antlr5-maven-plugin/pom.xml @@ -159,9 +159,9 @@ org.apache.maven.plugins maven-compiler-plugin - 17 - 17 - 17 + ${maven.compiler.release} + ${maven.compiler.source} + ${maven.compiler.target} diff --git a/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/Antlr5Mojo.java b/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/Antlr5Mojo.java index be200b70c..bf32a36c7 100644 --- a/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/Antlr5Mojo.java +++ b/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/Antlr5Mojo.java @@ -8,8 +8,7 @@ import org.antlr.v5.Tool; import org.antlr.v5.codegen.CodeGenerator; -import org.antlr.v5.runtime.misc.MultiMap; -import org.antlr.v5.runtime.misc.Utils; +import org.antlr.v5.runtime._unused.misc.MultiMap; import org.antlr.v5.tool.Grammar; import org.apache.maven.plugin.AbstractMojo; import org.apache.maven.plugin.MojoExecutionException; @@ -485,7 +484,7 @@ private static String getPackageName(String relativeFolderPath) { // intentionally blank } - return Utils.join(parts.iterator(), "."); + return String.join(".", parts); } public Set getIncludesPatterns() { diff --git a/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/MojoUtils.java b/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/MojoUtils.java index 6bb025051..b18c58ab6 100644 --- a/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/MojoUtils.java +++ b/antlr5-maven-plugin/src/main/java/org/antlr/mojo/antlr5/MojoUtils.java @@ -55,7 +55,7 @@ public static byte[] checksum(File file) throws IOException { * directory and reflect the input organization of the grammar files. * * @param sourceDirectory The source directory {@link File} object - * @param grammarFileName The full path to the input grammar file + * @param grammarFile The input grammar file * * @return The path to the grammar file relative to the source directory */ diff --git a/pom.xml b/pom.xml index 59ede4e5e..1c58e7496 100644 --- a/pom.xml +++ b/pom.xml @@ -91,9 +91,10 @@ UTF-8 1693865452 true - 11 - 11 - 2.0.0-Beta4 + 17 + 17 + 17 + 2.0.0-Beta4 5.9.0 diff --git a/runtime-testsuite/pom.xml b/runtime-testsuite/pom.xml index bf8e75bbb..783eff407 100644 --- a/runtime-testsuite/pom.xml +++ b/runtime-testsuite/pom.xml @@ -37,7 +37,7 @@ org.antlr - antlr5-runtime + antlr5-java-runtime ${project.version} test @@ -72,7 +72,7 @@ org.jetbrains.kotlin - kotlin-stdlib-jdk8 + kotlin-stdlib ${kotlin.version} @@ -189,9 +189,9 @@ - 17 - 17 - 17 + ${maven.compiler.release} + ${maven.compiler.source} + ${maven.compiler.target} diff --git a/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Java.test.stg b/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Java.test.stg index e81f75a19..b98c2af6a 100644 --- a/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Java.test.stg +++ b/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Java.test.stg @@ -44,7 +44,7 @@ ModMemberEquals(n,m,v) ::= <%this. % == %> ModMemberNotEquals(n,m,v) ::= <%this. % != %> -DumpDFA() ::= "this.dumpDFA(outStream);" +DumpDFA() ::= "this.dumpDFA(new IPrintStream() { public void print(String value) { outStream.print(value); } public void printLine(String value) { outStream.println(value); } });" Pass() ::= "" @@ -66,23 +66,23 @@ TextEquals(a) ::= <%this.getText().equals("")%> PlusText(a) ::= <%"" + this.getText()%> -InputText() ::= "this._input.getText()" +InputText() ::= "this.get_input().getText()" -LTEquals(i, v) ::= <%this._input.LT().getText().equals()%> +LTEquals(i, v) ::= <%this.get_input().LT().getText().equals()%> -LANotEquals(i, v) ::= <%this._input.LA()!=%> +LANotEquals(i, v) ::= <%this.get_input().LA()!=%> -TokenStartColumnEquals(i) ::= <%this._tokenStartCharPositionInLine==%> +TokenStartColumnEquals(i) ::= <%this.get_tokenStartCharPositionInLine()==%> ImportListener(X) ::= "" -GetExpectedTokenNames() ::= "this.getExpectedTokens().toString(this.tokenNames)" +GetExpectedTokenNames() ::= "this.getExpectedTokens().toString(this.getVocabulary())" ImportRuleInvocationStack() ::= "" -RuleInvocationStack() ::= "getRuleInvocationStack()" +RuleInvocationStack() ::= "getRuleInvocationStack(getContext())" -LL_EXACT_AMBIG_DETECTION() ::= <<_interp.setPredictionMode(PredictionMode.LL_EXACT_AMBIG_DETECTION);>> +LL_EXACT_AMBIG_DETECTION() ::= <> ParserToken(parser, token) ::= <%.%> @@ -106,8 +106,8 @@ PositionAdjustingLexer() ::= << @Override public Token nextToken() { - if (!(_interp instanceof PositionAdjustingLexerATNSimulator)) { - _interp = new PositionAdjustingLexerATNSimulator(this, _ATN, _decisionToDFA, _sharedContextCache); + if (!(getInterpreter() instanceof PositionAdjustingLexerATNSimulator)) { + setInterpreter(new PositionAdjustingLexerATNSimulator(this, _ATN, _decisionToDFA, _sharedContextCache)); } return super.nextToken(); @@ -115,7 +115,7 @@ public Token nextToken() { @Override public Token emit() { - switch (_type) { + switch (getType()) { case TOKENS: handleAcceptPositionForKeyword("tokens"); break; @@ -138,9 +138,10 @@ private boolean handleAcceptPositionForIdentifier() { identifierLength++; } - if (getInputStream().index() > _tokenStartCharIndex + identifierLength) { + if (getInputStream().index() > get_tokenStartCharIndex() + identifierLength) { int offset = identifierLength - 1; - getInterpreter().resetAcceptPosition(getInputStream(), _tokenStartCharIndex + offset, _tokenStartLine, _tokenStartCharPositionInLine + offset); + PositionAdjustingLexerATNSimulator simulator = (PositionAdjustingLexerATNSimulator)getInterpreter(); + simulator.resetAcceptPosition(getInputStream(), get_tokenStartCharIndex() + offset, get_tokenStartLine(), get_tokenStartCharPositionInLine() + offset); return true; } @@ -148,20 +149,16 @@ private boolean handleAcceptPositionForIdentifier() { } private boolean handleAcceptPositionForKeyword(String keyword) { - if (getInputStream().index() > _tokenStartCharIndex + keyword.length()) { + if (getInputStream().index() > get_tokenStartCharIndex() + keyword.length()) { int offset = keyword.length() - 1; - getInterpreter().resetAcceptPosition(getInputStream(), _tokenStartCharIndex + offset, _tokenStartLine, _tokenStartCharPositionInLine + offset); + PositionAdjustingLexerATNSimulator simulator = (PositionAdjustingLexerATNSimulator)getInterpreter(); + simulator.resetAcceptPosition(getInputStream(), get_tokenStartCharIndex() + offset, get_tokenStartLine(), get_tokenStartCharPositionInLine() + offset); return true; } return false; } -@Override -public PositionAdjustingLexerATNSimulator getInterpreter() { - return (PositionAdjustingLexerATNSimulator)super.getInterpreter(); -} - private static boolean isIdentifierChar(char c) { return Character.isLetterOrDigit(c) || c == '_'; } @@ -177,8 +174,8 @@ protected static class PositionAdjustingLexerATNSimulator extends LexerATNSimula protected void resetAcceptPosition(CharStream input, int index, int line, int charPositionInLine) { input.seek(index); - this.line = line; - this.charPositionInLine = charPositionInLine; + this.setLine(line); + this.setCharPositionInLine(charPositionInLine); consume(input); } @@ -233,10 +230,10 @@ RuleGetterListener(X) ::= << public class LeafListener extends TBaseListener { public void exitA(TParser.AContext ctx) { if (ctx.getChildCount()==2) { - outStream.printf("%s %s %s\n",ctx.b(0).start.getText(), - ctx.b(1).start.getText(),ctx.b().get(0).start.getText()); + outStream.printf("%s %s %s\n",ctx.b(0).getStart().getText(), + ctx.b(1).getStart().getText(),ctx.b().get(0).getStart().getText()); } else - outStream.println(ctx.b(0).start.getText()); + outStream.println(ctx.b(0).getStart().getText()); } } } @@ -248,8 +245,8 @@ LRListener(X) ::= << public class LeafListener extends TBaseListener { public void exitE(TParser.EContext ctx) { if (ctx.getChildCount()==3) { - outStream.printf("%s %s %s\n",ctx.e(0).start.getText(), - ctx.e(1).start.getText(), ctx.e().get(0).start.getText()); + outStream.printf("%s %s %s\n",ctx.e(0).getStart().getText(), + ctx.e(1).getStart().getText(), ctx.e().get(0).getStart().getText()); } else outStream.println(ctx.INT().getSymbol().getText()); } @@ -261,7 +258,7 @@ LRWithLabelsListener(X) ::= << @parser::members { public class LeafListener extends TBaseListener { public void exitCall(TParser.CallContext ctx) { - outStream.printf("%s %s\n",ctx.e().start.getText(),ctx.eList()); + outStream.printf("%s %s\n",ctx.e().getStart().getText(),ctx.eList()); } public void exitInt(TParser.IntContext ctx) { outStream.println(ctx.INT().getSymbol().getText()); diff --git a/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Kotlin.test.stg b/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Kotlin.test.stg index 941b071f5..1d98dfa98 100644 --- a/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Kotlin.test.stg +++ b/runtime-testsuite/resources/org/antlr/v5/test/runtime/templates/Kotlin.test.stg @@ -82,7 +82,7 @@ ImportRuleInvocationStack() ::= "" RuleInvocationStack() ::= "getRuleInvocationStack()" -LL_EXACT_AMBIG_DETECTION() ::= <> +LL_EXACT_AMBIG_DETECTION() ::= <> ParserToken(parser, token) ::= <%.Tokens.%> diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/ErrorQueue.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/ErrorQueue.java index b14ed6842..2caf7b50c 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/ErrorQueue.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/ErrorQueue.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime; import org.antlr.v5.Tool; -import org.antlr.v5.runtime.misc.Utils; +import org.antlr.v5.runtime.core.misc.Utils; import org.antlr.v5.tool.ANTLRMessage; import org.antlr.v5.tool.ANTLRToolListener; import org.antlr.v5.tool.ToolMessage; @@ -14,6 +14,7 @@ import java.util.ArrayList; import java.util.List; +import java.util.stream.Collectors; public class ErrorQueue implements ANTLRToolListener { public final Tool tool; @@ -63,7 +64,7 @@ public String toString() { public String toString(boolean rendered) { if (!rendered) { - return Utils.join(all.iterator(), "\n"); + return all.stream().map(Object::toString).collect(Collectors.joining("\n")); } if (tool == null) { diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/FileUtils.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/FileUtils.java index 725493671..ffafbe815 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/FileUtils.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/FileUtils.java @@ -6,11 +6,7 @@ package org.antlr.v5.test.runtime; -import org.antlr.v5.runtime.misc.Utils; - -import java.io.File; -import java.io.IOException; -import java.io.PrintWriter; +import java.io.*; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.LinkOption; @@ -18,28 +14,19 @@ import java.nio.file.attribute.BasicFileAttributes; import java.nio.file.attribute.DosFileAttributes; -import static org.antlr.v5.test.runtime.RuntimeTestUtils.FileSeparator; - public class FileUtils { - public static void writeFile(String dir, String fileName, String content) { - try { - Utils.writeFile(dir + FileSeparator + fileName, content, "UTF-8"); - } - catch (IOException ioe) { - System.err.println("can't write file"); - ioe.printStackTrace(System.err); - } - } - public static String readFile(String dir, String fileName) { + public static void writeFile(String fileName, String content, String encoding) { try { - return String.copyValueOf(Utils.readFile(dir+"/"+fileName, "UTF-8")); - } - catch (IOException ioe) { - System.err.println("can't read file"); + File f = new File(fileName); + FileOutputStream fos = new FileOutputStream(f); + try(OutputStreamWriter osw = encoding != null ? new OutputStreamWriter(fos, encoding) : new OutputStreamWriter(fos)) { + osw.write(content); + } + } catch (IOException ioe) { + System.err.println("can't write file"); ioe.printStackTrace(System.err); } - return null; } public static void replaceInFile(Path sourcePath, String target, String replacement) throws IOException { @@ -72,7 +59,7 @@ public static void deleteDirectory(File f) throws IOException { throw new IOException("Failed to delete file: " + f); } - public static boolean isLink(Path path) throws IOException { + public static boolean isLink(Path path) { try { BasicFileAttributes attrs = Files.readAttributes(path, BasicFileAttributes.class, LinkOption.NOFOLLOW_LINKS); return attrs.isSymbolicLink() || (attrs instanceof DosFileAttributes && attrs.isOther()); diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/Generator.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/Generator.java index b47c1815d..a7de7b96c 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/Generator.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/Generator.java @@ -11,6 +11,8 @@ import java.io.File; import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; import java.util.ArrayList; import java.util.Arrays; import java.util.List; @@ -27,7 +29,8 @@ public static GeneratedState generate(RunOptions runOptions, String language, St if (runOptions.slaveGrammars != null) { for (String grammar : runOptions.slaveGrammars) { GrammarFile slaveGrammarFile = parseGrammarFile(grammar); - writeFile(workingDirectory, slaveGrammarFile.grammarName + ".g4", slaveGrammarFile.content); + Path fullPath = Paths.get(workingDirectory, slaveGrammarFile.grammarName + ".g4"); + writeFile(fullPath.toString() , slaveGrammarFile.content, null); } } @@ -42,7 +45,8 @@ public static GeneratedState generate(RunOptions runOptions, String language, St final List options = new ArrayList<>(); for (GrammarFile grammarFile : grammarFiles) { - writeFile(workingDirectory, grammarFile.grammarName + ".g4", grammarFile.content); + Path fullPath = Paths.get(workingDirectory, grammarFile.grammarName + ".g4"); + writeFile(fullPath.toString(), grammarFile.content, null); if (grammarFile == mainFile) continue; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeRunner.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeRunner.java index 5afe3ff48..9fd2b4ff7 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeRunner.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeRunner.java @@ -115,6 +115,7 @@ public static String getRuntimePath(String language) { } public State run(RunOptions runOptions) { + GeneratedState generatedState = Generator.generate(runOptions, getLanguage(), getTempDirPath(), null); if (generatedState.containsErrors() || runOptions.endStage == Stage.Generate) { @@ -126,7 +127,11 @@ public State run(RunOptions runOptions) { return new CompiledState(generatedState, new Exception(getTitleName() + " ANTLR runtime is not initialized")); } - writeRecognizerFile(runOptions, generatedState); + try { + writeRecognizerFile(runOptions, generatedState); + } catch (IOException e) { + return new CompiledState(generatedState, e); + } CompiledState compiledState = compile(runOptions, generatedState); @@ -134,12 +139,16 @@ public State run(RunOptions runOptions) { return compiledState; } - writeInputFile(runOptions); + try { + writeInputFile(runOptions); + } catch (IOException e) { + return new CompiledState(generatedState, e); + } return execute(runOptions, compiledState); } - protected void writeRecognizerFile(RunOptions runOptions, GeneratedState generatedState) { + protected void writeRecognizerFile(RunOptions runOptions, GeneratedState generatedState) throws IOException { String text = RuntimeTestUtils.getTextFromResource("org/antlr/v5/test/runtime/helpers/" + getTestFileWithExt() + ".stg"); ST outputFileST = new ST(text); outputFileST.add("grammarName", generatedState.getMainGrammarFile().grammarName); @@ -206,7 +215,7 @@ protected CompiledState compile(RunOptions runOptions, GeneratedState generatedS return new CompiledState(generatedState, null); } - protected void writeInputFile(RunOptions runOptions) { + protected void writeInputFile(RunOptions runOptions) throws IOException { writeFile(getTempDirPath(), InputFileName, runOptions.input); } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptor.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptor.java index c7b70d347..84ce8394a 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptor.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptor.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime; -import org.antlr.v5.runtime.misc.Pair; +import kotlin.Pair; import java.net.URI; import java.util.Arrays; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptorParser.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptorParser.java index 52a570ab6..2a7194e38 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptorParser.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestDescriptorParser.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime; -import org.antlr.v5.runtime.misc.Pair; +import kotlin.Pair; import java.net.URI; import java.util.*; @@ -124,10 +124,10 @@ public static RuntimeTestDescriptor parse(String name, String text, URI uri) thr boolean buildParseTree = true; String[] skipTargets = new String[0]; for (Pair p : pairs) { - String section = p.a; + String section = p.getFirst(); String value = ""; - if ( p.b!=null ) { - value = p.b.trim(); + if ( p.getSecond()!=null ) { + value = p.getSecond().trim(); } if ( value.startsWith("\"\"\"") ) { value = value.replace("\"\"\"", ""); diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestUtils.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestUtils.java index 023343e63..cca8b7c6a 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestUtils.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTestUtils.java @@ -7,7 +7,7 @@ package org.antlr.v5.test.runtime; import org.antlr.v5.automata.ATNPrinter; -import org.antlr.v5.runtime.atn.ATNState; +import org.antlr.v5.runtime.core.state.ATNState; import org.antlr.v5.tool.Grammar; import org.antlr.v5.tool.Rule; @@ -97,7 +97,7 @@ public static synchronized String getTextFromResource(String name) { public static void checkRuleATN(Grammar g, String ruleName, String expecting) { Rule r = g.getRule(ruleName); - ATNState startState = g.getATN().ruleToStartState[r.index]; + ATNState startState = g.getATN().getRuleToStartState()[r.index]; ATNPrinter serializer = new ATNPrinter(g, startState); String result = serializer.asString(); diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTests.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTests.java index 0e6563e66..9bb1401f6 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTests.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/RuntimeTests.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime; -import org.antlr.v5.runtime.misc.Pair; +import kotlin.Pair; import org.antlr.v5.test.runtime.java.JavaRuntimeTests; import org.antlr.v5.test.runtime.states.ExecutedState; import org.antlr.v5.test.runtime.states.State; @@ -121,8 +121,8 @@ private static void test(RuntimeTestDescriptor descriptor, RuntimeRunner runner) Pair allGrammars = prepareGrammars(descriptor, runner); RunOptions runOptions = new RunOptions( - allGrammars.a, - allGrammars.b, + allGrammars.getFirst(), + allGrammars.getSecond(), true, true, descriptor.startRule, diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/misc/InterpreterDataReader.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/InterpreterDataReader.java similarity index 88% rename from runtime/Java/src/main/java/org/antlr/v5/runtime/misc/InterpreterDataReader.java rename to runtime-testsuite/test/org/antlr/v5/test/runtime/java/InterpreterDataReader.java index a7d57a610..01812dabd 100644 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/misc/InterpreterDataReader.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/InterpreterDataReader.java @@ -1,20 +1,20 @@ /* - * Copyright (c) 2012-present The ANTLR Project. All rights reserved. + * Copyright (c) 2012-2017 The ANTLR Project. All rights reserved. * Use of this file is governed by the BSD 3-clause license that * can be found in the LICENSE.txt file in the project root. */ -package org.antlr.v5.runtime.misc; +package org.antlr.v5.test.runtime.java; -import org.antlr.v5.runtime.Vocabulary; -import org.antlr.v5.runtime.VocabularyImpl; -import org.antlr.v5.runtime.atn.ATN; -import org.antlr.v5.runtime.atn.ATNDeserializer; +import org.antlr.v5.runtime.core.Vocabulary; +import org.antlr.v5.runtime.core.VocabularyImpl; +import org.antlr.v5.runtime.core.atn.ATN; +import org.antlr.v5.runtime.core.atn.ATNDeserializer; -import java.util.List; -import java.util.ArrayList; import java.io.BufferedReader; import java.io.FileReader; +import java.util.ArrayList; +import java.util.List; // A class to read plain text interpreter data produced by ANTLR. public class InterpreterDataReader { @@ -56,8 +56,8 @@ public static InterpreterData parseFile(String fileName) { try (BufferedReader br = new BufferedReader(new FileReader(fileName))) { String line; - List literalNames = new ArrayList(); - List symbolicNames = new ArrayList(); + List literalNames = new ArrayList<>(); + List symbolicNames = new ArrayList<>(); line = br.readLine(); if ( !line.equals("token literal names:") ) @@ -77,7 +77,7 @@ public static InterpreterData parseFile(String fileName) { symbolicNames.add(line.equals("null") ? "" : line); } - result.vocabulary = new VocabularyImpl(literalNames.toArray(new String[0]), symbolicNames.toArray(new String[0])); + result.vocabulary = new VocabularyImpl(literalNames.toArray(new String[0]), symbolicNames.toArray(new String[0]), null); line = br.readLine(); if ( !line.equals("rule names:") ) diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/JavaRunner.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/JavaRunner.java index 6fddd09c1..7528c204d 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/JavaRunner.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/JavaRunner.java @@ -6,10 +6,14 @@ package org.antlr.v5.test.runtime.java; import org.antlr.v5.runtime.*; -import org.antlr.v5.runtime.atn.PredictionMode; -import org.antlr.v5.runtime.atn.ParserATNSimulator; -import org.antlr.v5.runtime.atn.ProfilingATNSimulator; -import org.antlr.v5.runtime.tree.ParseTree; +import org.antlr.v5.runtime.core.CommonTokenStream; +import org.antlr.v5.runtime.core.Lexer; +import org.antlr.v5.runtime.core.Parser; +import org.antlr.v5.runtime.core.atn.PredictionMode; +import org.antlr.v5.runtime.core.atn.ParserATNSimulator; +import org.antlr.v5.runtime.core.atn.ProfilingATNSimulator; +import org.antlr.v5.runtime.core.context.ParserRuleContext; +import org.antlr.v5.runtime.core.tree.ParseTree; import org.antlr.v5.runtime.tree.ParseTreeWalker; import org.antlr.v5.test.runtime.*; import org.antlr.v5.test.runtime.java.helpers.CustomStreamErrorListener; @@ -129,7 +133,7 @@ protected ExecutedState execute(RunOptions runOptions, CompiledState compiledSta if (runOptions.traceATN) { // Setting trace_atn_sim isn't thread-safe, // But it's used only in helper TraceATN that is not integrated into tests infrastructure - ParserATNSimulator.trace_atn_sim = true; + ParserATNSimulator.Companion.setTrace_atn_sim(true); } ProfilingATNSimulator profiler = null; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestCharStreams.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestCharStreams.java index 40d2cb207..f82774466 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestCharStreams.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestCharStreams.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime.java; -import org.antlr.v5.runtime.CharStream; +import org.antlr.v5.runtime.core.CharStream; import org.antlr.v5.runtime.CharStreams; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.io.TempDir; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestIntegerList.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestIntegerList.java index abe0cca9c..94f8963eb 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestIntegerList.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestIntegerList.java @@ -6,7 +6,7 @@ package org.antlr.v5.test.runtime.java; -import org.antlr.v5.runtime.misc.IntegerList; +import org.antlr.v5.runtime.core.misc.IntegerList; import org.junit.jupiter.api.Test; import static org.junit.jupiter.api.Assertions.assertArrayEquals; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestInterpreterDataReader.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestInterpreterDataReader.java index d74070d7e..76f44def6 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestInterpreterDataReader.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/TestInterpreterDataReader.java @@ -7,13 +7,12 @@ package org.antlr.v5.test.runtime.java; import org.antlr.v5.Tool; -import org.antlr.v5.runtime.Vocabulary; -import org.antlr.v5.runtime.VocabularyImpl; -import org.antlr.v5.runtime.atn.ATN; -import org.antlr.v5.runtime.atn.ATNDeserializer; -import org.antlr.v5.runtime.atn.ATNSerializer; -import org.antlr.v5.runtime.misc.IntegerList; -import org.antlr.v5.runtime.misc.InterpreterDataReader; +import org.antlr.v5.runtime.core.Vocabulary; +import org.antlr.v5.runtime.core.VocabularyImpl; +import org.antlr.v5.runtime.core.atn.ATN; +import org.antlr.v5.runtime.core.atn.ATNDeserializer; +import org.antlr.v5.runtime.core.atn.ATNSerializer; +import org.antlr.v5.runtime.core.misc.IntegerList; import org.antlr.v5.tool.Grammar; import org.junit.jupiter.api.Test; @@ -81,7 +80,7 @@ public void testParseFile() throws IOException, NoSuchFieldException, IllegalAcc assertNull(channels); assertNull(modes); - IntegerList serialized = ATNSerializer.getSerialized(atn); + IntegerList serialized = ATNSerializer.Companion.getSerialized(atn); assertEquals(ATNDeserializer.SERIALIZED_VERSION, serialized.get(0)); } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/Java.g4 b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/Java.g4 index 0a747c4c3..b7f621538 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/Java.g4 +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/Java.g4 @@ -980,10 +980,10 @@ JavaLetter : [a-zA-Z$_] // these are the "java letters" below 0x7F | // covers all characters above 0x7F which are not a surrogate ~[\u0000-\u007F\uD800-\uDBFF] - {Character.isJavaIdentifierStart(_input.LA(-1))}? + {Character.isJavaIdentifierStart(get_input().LA(-1))}? | // covers UTF-16 surrogate pairs encodings for U+10000 to U+10FFFF [\uD800-\uDBFF] [\uDC00-\uDFFF] - {Character.isJavaIdentifierStart(Character.toCodePoint((char)_input.LA(-2), (char)_input.LA(-1)))}? + {Character.isJavaIdentifierStart(Character.toCodePoint((char)get_input().LA(-2), (char)get_input().LA(-1)))}? ; fragment @@ -991,10 +991,10 @@ JavaLetterOrDigit : [a-zA-Z0-9$_] // these are the "java letters or digits" below 0x7F | // covers all characters above 0x7F which are not a surrogate ~[\u0000-\u007F\uD800-\uDBFF] - {Character.isJavaIdentifierPart(_input.LA(-1))}? + {Character.isJavaIdentifierPart(get_input().LA(-1))}? | // covers UTF-16 surrogate pairs encodings for U+10000 to U+10FFFF [\uD800-\uDBFF] [\uDC00-\uDFFF] - {Character.isJavaIdentifierPart(Character.toCodePoint((char)_input.LA(-2), (char)_input.LA(-1)))}? + {Character.isJavaIdentifierPart(Character.toCodePoint((char)get_input().LA(-2), (char)get_input().LA(-1)))}? ; // diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestExpectedTokens.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestExpectedTokens.java index 817dcee80..05ebf9465 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestExpectedTokens.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestExpectedTokens.java @@ -5,9 +5,9 @@ */ package org.antlr.v5.test.runtime.java.api; -import org.antlr.v5.runtime.ParserRuleContext; -import org.antlr.v5.runtime.atn.ATN; -import org.antlr.v5.runtime.misc.IntervalSet; +import org.antlr.v5.runtime.core.context.ParserRuleContext; +import org.antlr.v5.runtime.core.atn.ATN; +import org.antlr.v5.runtime.core.misc.IntervalSet; import org.antlr.v5.test.runtime.RuntimeTestUtils; import org.antlr.v5.test.runtime.java.JavaRunner; import org.antlr.v5.tool.Grammar; @@ -34,7 +34,7 @@ public void testEpsilonAltSubrule() throws Exception { ATN atn = g.getATN(); int blkStartStateNumber = 3; IntervalSet tokens = atn.getExpectedTokens(blkStartStateNumber, null); - assertEquals("{B, C}", tokens.toString(g.getTokenNames())); + assertEquals("{B, C}", tokens.toString(g.getVocabulary())); } @Test public void testOptionalSubrule() throws Exception { @@ -54,7 +54,7 @@ public void testEpsilonAltSubrule() throws Exception { ATN atn = g.getATN(); int blkStartStateNumber = 3; IntervalSet tokens = atn.getExpectedTokens(blkStartStateNumber, null); - assertEquals("{B, C}", tokens.toString(g.getTokenNames())); + assertEquals("{B, C}", tokens.toString(g.getVocabulary())); } @Test public void testFollowIncluded() throws Exception { @@ -81,12 +81,12 @@ public void testEpsilonAltSubrule() throws Exception { // From the start of 'b' with empty stack, can only see B and EOF int blkStartStateNumber = 6; - IntervalSet tokens = atn.getExpectedTokens(blkStartStateNumber, ParserRuleContext.EMPTY); - assertEquals("{, B}", tokens.toString(g.getTokenNames())); + IntervalSet tokens = atn.getExpectedTokens(blkStartStateNumber, ParserRuleContext.getEMPTY()); + assertEquals("{, B}", tokens.toString(g.getVocabulary())); // Now call from 'a' - tokens = atn.getExpectedTokens(blkStartStateNumber, new ParserRuleContext(ParserRuleContext.EMPTY, 0)); - assertEquals("{A, B}", tokens.toString(g.getTokenNames())); + tokens = atn.getExpectedTokens(blkStartStateNumber, new ParserRuleContext(ParserRuleContext.getEMPTY(), 0)); + assertEquals("{A, B}", tokens.toString(g.getVocabulary())); } // Test for https://github.com/antlr/antlr4/issues/1480 @@ -134,11 +134,11 @@ public void testEpsilonAltSubrule() throws Exception { ParserRuleContext callStackFrom_expr = new ParserRuleContext(callStackFrom_s, 7); int afterID = 11; IntervalSet tokens = atn.getExpectedTokens(afterID, callStackFrom_expr); - assertEquals("{R, PLUS}", tokens.toString(g.getTokenNames())); + assertEquals("{R, PLUS}", tokens.toString(g.getVocabulary())); // Simulate call stack after input '(x' from within rule expr callStackFrom_expr = new ParserRuleContext(null, 7); tokens = atn.getExpectedTokens(afterID, callStackFrom_expr); - assertEquals("{R, PLUS}", tokens.toString(g.getTokenNames())); + assertEquals("{R, PLUS}", tokens.toString(g.getVocabulary())); } } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStream.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStream.java index ef48b46a6..1ca2db8e0 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStream.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStream.java @@ -5,7 +5,8 @@ */ package org.antlr.v5.test.runtime.java.api; -import org.antlr.v5.runtime.*; +import org.antlr.v5.runtime.CharStreams; +import org.antlr.v5.runtime.core.*; import org.junit.jupiter.api.Test; import static org.junit.jupiter.api.Assertions.assertEquals; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStreamRewriter.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStreamRewriter.java index beaf1ced5..436e43d9f 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStreamRewriter.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestTokenStreamRewriter.java @@ -6,7 +6,9 @@ package org.antlr.v5.test.runtime.java.api; import org.antlr.v5.runtime.*; -import org.antlr.v5.runtime.misc.Interval; +import org.antlr.v5.runtime.core.CommonTokenStream; +import org.antlr.v5.runtime.core.LexerInterpreter; +import org.antlr.v5.runtime.core.misc.Interval; import org.antlr.v5.tool.LexerGrammar; import org.junit.jupiter.api.Test; @@ -150,11 +152,11 @@ public void testInsertBeforeIndex0() throws Exception { expecting = "x = 0;"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(0, 9)); + result = tokens.getText(Interval.Companion.of(0, 9)); expecting = "x = 0;"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(4, 8)); + result = tokens.getText(Interval.Companion.of(4, 8)); expecting = "0"; assertEquals(expecting, result); } @@ -188,28 +190,28 @@ public void testInsertBeforeIndex0() throws Exception { expecting = "x = 0 + 2 * 0;"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(0, 17)); + result = tokens.getText(Interval.Companion.of(0, 17)); expecting = "x = 0 + 2 * 0;"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(4, 8)); + result = tokens.getText(Interval.Companion.of(4, 8)); expecting = "0"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(0, 8)); + result = tokens.getText(Interval.Companion.of(0, 8)); expecting = "x = 0"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(12, 16)); + result = tokens.getText(Interval.Companion.of(12, 16)); expecting = "2 * 0"; assertEquals(expecting, result); tokens.insertAfter(17, "// comment"); - result = tokens.getText(Interval.of(12, 18)); + result = tokens.getText(Interval.Companion.of(12, 18)); expecting = "2 * 0;// comment"; assertEquals(expecting, result); - result = tokens.getText(Interval.of(0, 8)); + result = tokens.getText(Interval.Companion.of(0, 8)); stream.fill(); // try again after insert at end expecting = "x = 0"; @@ -499,7 +501,7 @@ public void testInsertBeforeIndex0() throws Exception { stream.fill(); TokenStreamRewriter tokens = new TokenStreamRewriter(stream); tokens.replace(2, 4, "xyz"); - String result = tokens.getText(Interval.of(0, 6)); + String result = tokens.getText(Interval.Companion.of(0, 6)); String expecting = "abxyzba"; assertEquals(expecting, result); } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestVisitors.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestVisitors.java index d476c073b..991d8ae12 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestVisitors.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/TestVisitors.java @@ -5,11 +5,14 @@ */ package org.antlr.v5.test.runtime.java.api; -import org.antlr.v5.runtime.*; -import org.antlr.v5.runtime.tree.AbstractParseTreeVisitor; -import org.antlr.v5.runtime.tree.ErrorNode; -import org.antlr.v5.runtime.tree.RuleNode; -import org.antlr.v5.runtime.tree.TerminalNode; +import org.antlr.v5.runtime.BaseErrorListener; +import org.antlr.v5.runtime.CharStreams; +import org.antlr.v5.runtime.core.CommonTokenStream; +import org.antlr.v5.runtime.core.Recognizer; +import org.antlr.v5.runtime.core.error.RecognitionException; +import org.antlr.v5.runtime.core.tree.ErrorNode; +import org.antlr.v5.runtime.core.tree.RuleNode; +import org.antlr.v5.runtime.core.tree.TerminalNode; import org.junit.jupiter.api.Test; import java.util.ArrayList; @@ -32,10 +35,10 @@ public void testVisitTerminalNode() { VisitorBasicParser.SContext context = parser.s(); assertEquals("(s A )", context.toStringTree(parser)); - VisitorBasicVisitor listener = new VisitorBasicBaseVisitor() { + VisitorBasicVisitor visitor = new VisitorBasicBaseVisitor<>() { @Override public String visitTerminal(TerminalNode node) { - return node.getSymbol().toString() + "\n"; + return node.getSymbol() + "\n"; } @Override @@ -49,7 +52,7 @@ protected String aggregateResult(String aggregate, String nextResult) { } }; - String result = listener.visit(context); + String result = visitor.visit(context); String expected = "[@0,0:0='A',<1>,1:0]\n" + "[@1,1:0='',<-1>,1:1]\n"; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/perf/TimeLexerSpeed.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/perf/TimeLexerSpeed.java index 1c0c511ab..5ba4f2086 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/perf/TimeLexerSpeed.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/api/perf/TimeLexerSpeed.java @@ -6,10 +6,10 @@ package org.antlr.v5.test.runtime.java.api.perf; -import org.antlr.v5.runtime.CharStream; import org.antlr.v5.runtime.CharStreams; -import org.antlr.v5.runtime.CommonTokenStream; -import org.antlr.v5.runtime.Lexer; +import org.antlr.v5.runtime.core.CharStream; +import org.antlr.v5.runtime.core.CommonTokenStream; +import org.antlr.v5.runtime.core.Lexer; import org.antlr.v5.test.runtime.java.api.JavaLexer; import org.openjdk.jol.info.GraphLayout; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/CustomStreamErrorListener.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/CustomStreamErrorListener.java index 5bae05aa7..4acccdb13 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/CustomStreamErrorListener.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/CustomStreamErrorListener.java @@ -1,8 +1,8 @@ package org.antlr.v5.test.runtime.java.helpers; import org.antlr.v5.runtime.BaseErrorListener; -import org.antlr.v5.runtime.RecognitionException; -import org.antlr.v5.runtime.Recognizer; +import org.antlr.v5.runtime.core.error.RecognitionException; +import org.antlr.v5.runtime.core.Recognizer; import java.io.PrintStream; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestLexer.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestLexer.java index 81836854c..41cd82511 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestLexer.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestLexer.java @@ -1,7 +1,7 @@ package org.antlr.v5.test.runtime.java.helpers; -import org.antlr.v5.runtime.CharStream; -import org.antlr.v5.runtime.Lexer; +import org.antlr.v5.runtime.core.CharStream; +import org.antlr.v5.runtime.core.Lexer; public abstract class RuntimeTestLexer extends Lexer { protected java.io.PrintStream outStream = System.out; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestParser.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestParser.java index 3c41a129c..2a4bdf04d 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestParser.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/RuntimeTestParser.java @@ -1,7 +1,7 @@ package org.antlr.v5.test.runtime.java.helpers; -import org.antlr.v5.runtime.Parser; -import org.antlr.v5.runtime.TokenStream; +import org.antlr.v5.runtime.core.Parser; +import org.antlr.v5.runtime.core.TokenStream; public abstract class RuntimeTestParser extends Parser { protected java.io.PrintStream outStream = System.out; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/TreeShapeListener.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/TreeShapeListener.java index 8f9fbdfb2..eb386b5cb 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/TreeShapeListener.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/java/helpers/TreeShapeListener.java @@ -1,7 +1,7 @@ package org.antlr.v5.test.runtime.java.helpers; -import org.antlr.v5.runtime.ParserRuleContext; -import org.antlr.v5.runtime.tree.*; +import org.antlr.v5.runtime.core.context.ParserRuleContext; +import org.antlr.v5.runtime.core.tree.*; public class TreeShapeListener implements ParseTreeListener { public static final TreeShapeListener INSTANCE = new TreeShapeListener(); diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/javascript/NodeRunner.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/javascript/NodeRunner.java index b6ed923be..8566dbd8b 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/javascript/NodeRunner.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/javascript/NodeRunner.java @@ -41,7 +41,8 @@ protected CompiledState compile(RunOptions runOptions, GeneratedState generatedS } writeFile(getTempDirPath(), "package.json", - RuntimeTestUtils.getTextFromResource("org/antlr/v5/test/runtime/helpers/package_js.json")); + RuntimeTestUtils.getTextFromResource("org/antlr/v5/test/runtime/helpers/package_js.json")); + return new CompiledState(generatedState, null); } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/kotlin/helpers/TreeShapeListener.kt b/runtime-testsuite/test/org/antlr/v5/test/runtime/kotlin/helpers/TreeShapeListener.kt index 6fb9dde0b..91c41a226 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/kotlin/helpers/TreeShapeListener.kt +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/kotlin/helpers/TreeShapeListener.kt @@ -14,7 +14,7 @@ class TreeShapeListener : ParseTreeListener { override fun enterEveryRule(ctx: ParserRuleContext) { for (i in 0 until ctx.childCount) { - val parent = ctx.getChild(i)!!.readParent() + val parent = ctx.getChild(i)!!.getParent() check(!(parent !is RuleNode || parent.ruleContext !== ctx)) { "Invalid parse tree shape detected." } } } diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaCompiledState.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaCompiledState.java index 14bf376e0..2ed604b3c 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaCompiledState.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaCompiledState.java @@ -1,7 +1,12 @@ package org.antlr.v5.test.runtime.states.jvm; -import org.antlr.v5.runtime.*; -import org.antlr.v5.runtime.misc.Pair; +import kotlin.Pair; +import org.antlr.v5.runtime.CharStreams; +import org.antlr.v5.runtime.core.CharStream; +import org.antlr.v5.runtime.core.TokenStream; +import org.antlr.v5.runtime.core.CommonTokenStream; +import org.antlr.v5.runtime.core.Lexer; +import org.antlr.v5.runtime.core.Parser; import org.antlr.v5.test.runtime.RuntimeRunner; import org.antlr.v5.test.runtime.states.GeneratedState; diff --git a/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaExecutedState.java b/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaExecutedState.java index 26b827d6d..e47b4e3ea 100644 --- a/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaExecutedState.java +++ b/runtime-testsuite/test/org/antlr/v5/test/runtime/states/jvm/JavaExecutedState.java @@ -1,6 +1,6 @@ package org.antlr.v5.test.runtime.states.jvm; -import org.antlr.v5.runtime.tree.ParseTree; +import org.antlr.v5.runtime.core.tree.ParseTree; public class JavaExecutedState extends JvmExecutedState { public JavaExecutedState(JavaCompiledState previousState, String output, String errors, ParseTree parseTree, Exception exception) { diff --git a/runtime/Core/pom.xml b/runtime/Core/pom.xml index c6b5cd870..ac6bc9c63 100644 --- a/runtime/Core/pom.xml +++ b/runtime/Core/pom.xml @@ -23,7 +23,7 @@ org.jetbrains.kotlin - kotlin-stdlib-jdk8 + kotlin-stdlib ${kotlin.version} @@ -90,7 +90,7 @@ - 17 + ${maven.compiler.target} -Xmulti-platform -Xexpect-actual-classes @@ -115,9 +115,9 @@ - 17 - 17 - 17 + ${maven.compiler.release} + ${maven.compiler.source} + ${maven.compiler.target} diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/CommonToken.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/CommonToken.kt index 9d53d0edb..ef055a24b 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/CommonToken.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/CommonToken.kt @@ -98,7 +98,16 @@ public open class CommonToken : WritableToken { source = EMPTY_SOURCE } - /** + @Suppress("LeakingThis") + public constructor(type: Int, text: String, channel: Int) { + this.type = type + this.text = text + this.channel = channel + source = EMPTY_SOURCE + } + + + /** * Constructs a new [CommonToken] as a copy of another [Token]. * * If [oldToken] is also a [CommonToken] instance, the newly diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Lexer.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Lexer.kt index dde357b3a..87215537a 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Lexer.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Lexer.kt @@ -119,15 +119,15 @@ public abstract class Lexer(input: CharStream) : Recognizer private val _channelNames: Array private val _modeNames: Array - private var _interpreter: LexerATNSimulator + private var _interpreter: LexerATNSimulator? - override var interpreter: LexerATNSimulator + override var interpreter: LexerATNSimulator? get() = _interpreter set(value) { _interpreter = value diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Parser.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Parser.kt index a88cb59ba..59a9ea872 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Parser.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Parser.kt @@ -163,7 +163,7 @@ public abstract class Parser(input: TokenStream) : Recognizer get() = _parseListeners - override var tokenFactory: TokenFactory<*> + override var tokenFactory: TokenFactory get() = _input.tokenSource.tokenFactory set(value) { _input.tokenSource.tokenFactory = value @@ -233,7 +233,7 @@ public abstract class Parser(input: TokenStream) : Recognizer - get() = org.antlr.v5.runtime.core.jvm.synchronized(interpreter.decisionToDFA) { + get() = org.antlr.v5.runtime.core.jvm.synchronized(interpreter!!.decisionToDFA) { val s = ArrayList() - for (d in 0.. = Array(atn.maxTokenType) { vocabulary.getDisplayName(it) } private val _ruleNames: Array = ruleNames.toTypedArray() @@ -67,7 +67,7 @@ public open class ParserInterpreter( * Those values are used to create new recursive rule invocation contexts * associated with left operand of an alt like `"expr '*' expr"`. */ - protected val _parentContextStack: ArrayDeque> = ArrayDeque() + protected val _parentContextStack: ArrayDeque> = ArrayDeque() /** * We need a map from (decision, inputIndex) -> forced alt for computing ambiguous @@ -84,7 +84,7 @@ public open class ParserInterpreter( get() = atn.states[state] - override var interpreter: ParserATNSimulator + override var interpreter: ParserATNSimulator? get() = _interpreter set(value) { _interpreter = value @@ -106,7 +106,7 @@ public open class ParserInterpreter( * This tells us what the root of the parse tree is when using override * for an ambiguity/lookahead check. */ - public var overrideDecisionRoot: InterpreterRuleContext? = null + open var overrideDecisionRoot: InterpreterRuleContext? = null protected set /** @@ -188,7 +188,7 @@ public open class ParserInterpreter( } override fun enterRecursionRule(localctx: ParserRuleContext, state: Int, ruleIndex: Int, precedence: Int) { - val pair = Pair(context!!, localctx.invokingState) + val pair = Pair(context, localctx.invokingState) _parentContextStack.addFirst(pair) super.enterRecursionRule(localctx, state, ruleIndex, precedence) } @@ -295,7 +295,7 @@ public open class ParserInterpreter( predictedAlt = overrideDecisionAlt overrideDecisionReached = true } else { - predictedAlt = interpreter.adaptivePredict(_input, decision, context) + predictedAlt = interpreter!!.adaptivePredict(_input, decision, context) } } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Recognizer.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Recognizer.kt index 88eeabb31..cea2b0396 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Recognizer.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/Recognizer.kt @@ -43,7 +43,7 @@ public abstract class Recognizer { /** * The ATN interpreter used by the recognizer for prediction. */ - public abstract var interpreter: ATNInterpreter + public abstract var interpreter: ATNInterpreter? /** * Used to print out token names like ID during debugging and error reporting. @@ -159,7 +159,7 @@ public abstract class Recognizer { public val errorListenerDispatch: ANTLRErrorListener get() = ProxyErrorListener(errorListeners) - public abstract var tokenFactory: TokenFactory<*> + public abstract var tokenFactory: TokenFactory public fun getTokenType(tokenName: String): Int { val ttype = tokenTypeMap[tokenName] @@ -245,4 +245,7 @@ public abstract class Recognizer { ) { // Noop } + + public abstract val sourceName: String + get } diff --git a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/RuntimeMetaData.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/RuntimeMetaData.kt similarity index 97% rename from runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/RuntimeMetaData.kt rename to runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/RuntimeMetaData.kt index aa92e8144..ce1b3a30d 100644 --- a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/RuntimeMetaData.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/RuntimeMetaData.kt @@ -4,10 +4,10 @@ * can be found in the LICENSE.txt file in the project root. */ -package org.antlr.v5.runtime.kotlin +package org.antlr.v5.runtime.core -import org.antlr.v5.runtime.kotlin.RuntimeMetaData.checkVersion -import org.antlr.v5.runtime.kotlin.RuntimeMetaData.runtimeVersion +import org.antlr.v5.runtime.core.RuntimeMetaData.checkVersion +import org.antlr.v5.runtime.core.RuntimeMetaData.runtimeVersion import kotlin.math.min /** diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/TokenSource.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/TokenSource.kt index 28d261517..dca9eff75 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/TokenSource.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/TokenSource.kt @@ -63,7 +63,7 @@ public interface TokenSource { * The [TokenFactory] this token source is currently using for * creating [Token] objects from the input. */ - public var tokenFactory: TokenFactory<*> + public var tokenFactory: TokenFactory /** * Return a [Token] object from your input stream (usually a [CharStream]). diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATN.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATN.kt index c865e3275..a791d37d9 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATN.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATN.kt @@ -99,9 +99,11 @@ public class ATN(public val grammarType: ATNType, public val maxTokenType: Int) states.add(state) } - public fun removeState(state: ATNState) { + public fun removeState(state: ATNState): ATNState? { // Just free mem, don't shift states in list + var removing = states[state.stateNumber] states[state.stateNumber] = null + return removing } public fun defineDecisionState(s: DecisionState): Int { @@ -177,7 +179,7 @@ public class ATN(public val grammarType: ATNType, public val maxTokenType: Int) following = nextTokens(rt.followState) expected.addAll(following) expected.remove(Token.EPSILON) - ctx = ctx.readParent() + ctx = ctx.getParent() } if (following.contains(Token.EPSILON)) { diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNDeserializer.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNDeserializer.kt index 93aa27d31..1d4fa5557 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNDeserializer.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNDeserializer.kt @@ -9,9 +9,11 @@ package org.antlr.v5.runtime.core.atn import org.antlr.v5.runtime.core.Token import org.antlr.v5.runtime.core.action.* import org.antlr.v5.runtime.core.misc.IntervalSet +import org.antlr.v5.runtime.core.misc.decodeIntsEncodedAs16BitWords import org.antlr.v5.runtime.core.state.* import org.antlr.v5.runtime.core.transition.* + /** * @author Sam Harwell */ @@ -264,8 +266,8 @@ public open class ATNDeserializer(deserializationOptions: ATNDeserializationOpti var endState: ATNState? var excludeTransition: Transition? = null - - if (atn.ruleToStartState!![i].isLeftRecursiveRule) { + val ruleStartState = atn.ruleToStartState!![i] + if (ruleStartState.isLeftRecursiveRule) { // Wrap from the beginning of the rule to the StarLoopEntryState endState = null @@ -284,7 +286,7 @@ public open class ATNDeserializer(deserializationOptions: ATNDeserializationOpti continue } - if (maybeLoopEndState.epsilonOnlyTransitions && maybeLoopEndState.transition(0).target is RuleStopState) { + if (maybeLoopEndState.onlyHasEpsilonTransitions() && maybeLoopEndState.transition(0).target is RuleStopState) { endState = state break } @@ -313,19 +315,30 @@ public open class ATNDeserializer(deserializationOptions: ATNDeserializationOpti } // All transitions leaving the rule start state need to leave blockStart instead - while (atn.ruleToStartState!![i].numberOfTransitions > 0) { - val transition = atn.ruleToStartState!![i].removeTransition(atn.ruleToStartState!![i].numberOfTransitions - 1) + while (ruleStartState.numberOfTransitions > 0) { + val transition = ruleStartState.removeTransition(ruleStartState.numberOfTransitions - 1) bypassStart.addTransition(transition) } // Link the new states - atn.ruleToStartState!![i].addTransition(EpsilonTransition(bypassStart)) + ruleStartState.addTransition(EpsilonTransition(bypassStart)) bypassStop.addTransition(EpsilonTransition(endState!!)) val matchState = BasicState() atn.addState(matchState) matchState.addTransition(AtomTransition(bypassStop, atn.ruleToTokenType!![i])) - bypassStart.addTransition(EpsilonTransition(matchState)) + + if (bypassStart.onlyHasEpsilonTransitions()) { + bypassStart.addTransition(EpsilonTransition(matchState)) + } else { + val matchState2: ATNState = BasicState() + atn.addState(matchState2) + matchState2.addTransition(bypassStart.transition(0)) + + bypassStart.removeTransition(0) + bypassStart.addTransition(EpsilonTransition(matchState)) + bypassStart.addTransition(EpsilonTransition(matchState2)) + } } if (deserializationOptions.isVerifyATN) { @@ -383,7 +396,7 @@ public open class ATNDeserializer(deserializationOptions: ATNDeserializationOpti val maybeLoopEndState = state.transition(state.numberOfTransitions - 1).target if (maybeLoopEndState is LoopEndState) { - if (maybeLoopEndState.epsilonOnlyTransitions && maybeLoopEndState.transition(0).target is RuleStopState) { + if (maybeLoopEndState.onlyHasEpsilonTransitions() && maybeLoopEndState.transition(0).target is RuleStopState) { state.isPrecedenceDecision = true } } @@ -544,42 +557,5 @@ public open class ATNDeserializer(deserializationOptions: ATNDeserializationOpti LexerActionType.TYPE -> LexerTypeAction(data1) } - public open fun decodeIntsEncodedAs16BitWords(data16: CharArray): IntArray = - decodeIntsEncodedAs16BitWords(data16, false) - - /** - * Convert a list of chars (16 uint) that represent a serialized and compressed list of ints for an ATN. - */ - public open fun decodeIntsEncodedAs16BitWords(data16: CharArray, trimToSize: Boolean): IntArray { - // Will be strictly smaller, but we waste bit of space to avoid copying during initialization of parsers - val data = IntArray(data16.size) - var i = 0 - var i2 = 0 - - while (i < data16.size) { - val v = data16[i++] - - if (v.code and 0x8000 == 0) { - // Hi-bit not set? Implies 1-word value - // 7 bit int - data[i2++] = v.code - } else { - // Hi.bit set. Implies 2-word value - val vnext = data16[i++] - - if (v.code == 0xFFFF && vnext.code == 0xFFFF) { // Is it -1? - data[i2++] = -1 - } else { - // 31-bit int - data[i2++] = (v.code and 0x7FFF) shl 16 or (vnext.code and 0xFFFF) - } - } - } - - if (trimToSize) { - return data.copyOf(i2) - } - return data - } } diff --git a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/ATNSerializer.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNSerializer.kt similarity index 98% rename from runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/ATNSerializer.kt rename to runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNSerializer.kt index 22381d876..c759b46f0 100644 --- a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/ATNSerializer.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ATNSerializer.kt @@ -4,14 +4,11 @@ * can be found in the LICENSE.txt file in the project root. */ -package org.antlr.v5.runtime.kotlin._unused.atn +package org.antlr.v5.runtime.core.atn import org.antlr.v5.runtime.core.misc.assert import org.antlr.v5.runtime.core.Token import org.antlr.v5.runtime.core.action.* -import org.antlr.v5.runtime.core.atn.ATN -import org.antlr.v5.runtime.core.atn.ATNDeserializer -import org.antlr.v5.runtime.core.atn.ATNType import org.antlr.v5.runtime.core.misc.IntegerList import org.antlr.v5.runtime.core.misc.IntervalSet import org.antlr.v5.runtime.core.state.* diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/LexerATNSimulator.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/LexerATNSimulator.kt index 499b045cd..ee9aa5ac3 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/LexerATNSimulator.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/LexerATNSimulator.kt @@ -34,7 +34,7 @@ public open class LexerATNSimulator( protected val recog: Lexer?, atn: ATN, public val decisionToDFA: Array, - sharedContextCache: PredictionContextCache, + sharedContextCache: PredictionContextCache?, ) : ATNSimulator(atn, sharedContextCache) { public companion object { @Suppress("ConstPropertyName") @@ -106,7 +106,7 @@ public open class LexerATNSimulator( public constructor( atn: ATN, decisionToDFA: Array, - sharedContextCache: PredictionContextCache, + sharedContextCache: PredictionContextCache?, ) : this(null, atn, decisionToDFA, sharedContextCache) public open fun copyState(simulator: LexerATNSimulator) { @@ -752,17 +752,17 @@ public open class LexerATNSimulator( } val dfa = decisionToDFA[mode] - synchronized(dfa.states) { - val existing = dfa.states[proposed] + synchronized(dfa.getStatesMap()) { + val existing = dfa.getStatesMap()[proposed] if (existing != null) { return existing } - proposed.stateNumber = dfa.states.size + proposed.stateNumber = dfa.getStatesMap().size configs.isReadonly = true proposed.configs = configs - dfa.states[proposed] = proposed + dfa.getStatesMap()[proposed] = proposed return proposed } } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ParserATNSimulator.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ParserATNSimulator.kt index 92ff1a65a..4e8529906 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ParserATNSimulator.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ParserATNSimulator.kt @@ -369,7 +369,7 @@ public open class ParserATNSimulator( } } - val alt = execATN(dfa, s0, input, index, tempOuterContext!!) + val alt = execATN(dfa, s0, input, index, tempOuterContext) if (debug) { System.out.println("DFA after predictATN: ${dfa.toString(parser!!.vocabulary)}") @@ -424,7 +424,7 @@ public open class ParserATNSimulator( s0: DFAState, input: TokenStream, startIndex: Int, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, ): Int { if (debug || trace_atn_sim) { System.out.println( @@ -656,7 +656,7 @@ public open class ParserATNSimulator( s0: ATNConfigSet, input: TokenStream, startIndex: Int, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, ): Int { if (debug || trace_atn_sim) { System.out.println("execATNWithFullContext $s0") @@ -971,7 +971,7 @@ public open class ParserATNSimulator( return result } - protected open fun computeStartState(p: ATNState, ctx: RuleContext, fullCtx: Boolean): ATNConfigSet { + protected open fun computeStartState(p: ATNState, ctx: RuleContext?, fullCtx: Boolean): ATNConfigSet { // Always at least the implicit call to start rule val initialContext = PredictionContext.fromRuleContext(atn, ctx) val configs = ATNConfigSet(fullCtx) @@ -1318,7 +1318,7 @@ public open class ParserATNSimulator( */ protected open fun getSynValidOrSemInvalidAltThatFinishedDecisionEntryRule( configs: ATNConfigSet, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, ): Int { val sets = splitAccordingToSemanticValidity(configs, outerContext) val semValidConfigs = sets.first @@ -1373,7 +1373,7 @@ public open class ParserATNSimulator( */ protected fun splitAccordingToSemanticValidity( configs: ATNConfigSet, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, ): Pair { val succeeded = ATNConfigSet(configs.fullCtx) val failed = ATNConfigSet(configs.fullCtx) @@ -1407,7 +1407,7 @@ public open class ParserATNSimulator( */ public open fun evalSemanticContext( predPredictions: Array, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, complete: Boolean, ): BitSet { val predictions = BitSet() @@ -2162,7 +2162,7 @@ public open class ParserATNSimulator( protected open fun noViableAlt( input: TokenStream, - outerContext: ParserRuleContext, + outerContext: ParserRuleContext?, configs: ATNConfigSet, startIndex: Int, ): NoViableAltException = @@ -2250,8 +2250,8 @@ public open class ParserATNSimulator( return D } - synchronized(dfa.states) { - val existing = dfa.states[D] + synchronized(dfa.getStatesMap()) { + val existing = dfa.getStatesMap()[D] if (existing != null) { if (trace_atn_sim) { @@ -2261,7 +2261,7 @@ public open class ParserATNSimulator( return existing } - D.stateNumber = dfa.states.size + D.stateNumber = dfa.getStatesMap().size if (!D.configs.isReadonly) { D.configs.optimizeConfigs(this) @@ -2272,7 +2272,7 @@ public open class ParserATNSimulator( System.out.println("addDFAState new $D") } - dfa.states[D] = D + dfa.getStatesMap()[D] = D return D } } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ProfilingATNSimulator.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ProfilingATNSimulator.kt index 66bc16d64..f7e5ec0df 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ProfilingATNSimulator.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/atn/ProfilingATNSimulator.kt @@ -23,9 +23,9 @@ import kotlin.time.measureTimedValue @Suppress("PropertyName", "MemberVisibilityCanBePrivate") public open class ProfilingATNSimulator(parser: Parser) : ParserATNSimulator( parser, - parser.interpreter.atn, - parser.interpreter.decisionToDFA, - parser.interpreter.sharedContextCache!!, + parser.interpreter!!.atn, + parser.interpreter!!.decisionToDFA, + parser.interpreter!!.sharedContextCache!!, ) { protected var numDecisions: Int = 0 protected var _sllStopIndex: Int = 0 diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/InterpreterRuleContext.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/InterpreterRuleContext.kt index ea017635f..d97ce93c8 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/InterpreterRuleContext.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/InterpreterRuleContext.kt @@ -17,8 +17,8 @@ package org.antlr.v5.runtime.core.context * parser, this class (with slightly more memory overhead per node) is used to * provide equivalent functionality. */ -public class InterpreterRuleContext : ParserRuleContext { - override val ruleIndex: Int +open class InterpreterRuleContext : ParserRuleContext { + final override val ruleIndex: Int public constructor() { ruleIndex = -1 diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/ParserRuleContext.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/ParserRuleContext.kt index 8c3f58a51..3212846dd 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/ParserRuleContext.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/ParserRuleContext.kt @@ -107,8 +107,8 @@ public open class ParserRuleContext : RuleContext { public constructor() public constructor(parent: ParserRuleContext?, invokingStateNumber: Int) : super(parent, invokingStateNumber) - override fun readParent(): ParserRuleContext? = - super.readParent() as ParserRuleContext? + override fun getParent(): ParserRuleContext? = + super.getParent() as ParserRuleContext? /** * Copy a context (I'm deliberately not using copy constructor) to avoid @@ -124,7 +124,7 @@ public open class ParserRuleContext : RuleContext { * the `YContext` as well else they are lost! */ public open fun copyFrom(ctx: ParserRuleContext) { - parent = ctx.parent + setParent(ctx.getParent()) invokingState = ctx.invokingState start = ctx.start @@ -159,7 +159,7 @@ public open class ParserRuleContext : RuleContext { * Other [addChild] methods call this. * * We cannot set the parent pointer of the incoming node - * because the existing interfaces do not have a [assignParent] + * because the existing interfaces do not have a [setParent] * method and I don't want to break backward compatibility for this. * * @since 4.7 @@ -183,7 +183,7 @@ public open class ParserRuleContext : RuleContext { * Add a token leaf node child and force its parent to be this node. */ public fun addChild(t: TerminalNode): TerminalNode { - t.assignParent(this) + t.setParent(this) return addAnyChild(t) } @@ -193,7 +193,7 @@ public open class ParserRuleContext : RuleContext { * @since 4.7 */ public fun addErrorNode(errorNode: ErrorNode): ErrorNode { - errorNode.assignParent(this) + errorNode.setParent(this) return addAnyChild(errorNode) } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/PredictionContext.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/PredictionContext.kt index edf57297a..aeb1ffed0 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/PredictionContext.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/PredictionContext.kt @@ -65,12 +65,12 @@ public abstract class PredictionContext protected constructor( // If we are in RuleContext of start rule, s, then PredictionContext // is EMPTY. Nobody called us. (if we are empty, return empty) - if (tempOuterContext.parent == null || tempOuterContext === ParserRuleContext.EMPTY) { + if (tempOuterContext.getParent() == null || tempOuterContext === ParserRuleContext.EMPTY) { return EmptyPredictionContext.Instance } // If we have a parent, convert it to a PredictionContext graph - val parent = fromRuleContext(atn, tempOuterContext.readParent()) + val parent = fromRuleContext(atn, tempOuterContext.getParent()) val state = atn.states[tempOuterContext.invokingState] val transition = state!!.transition(0) as RuleTransition return SingletonPredictionContext.create(parent, transition.followState.stateNumber) @@ -519,9 +519,7 @@ public abstract class PredictionContext protected constructor( return b } - // Note(Edoardo): we should be sure there are no null elements inside this array - @Suppress("UNCHECKED_CAST") - combineCommonParents(mergedParents as Array) + combineCommonParents(mergedParents) mergeCache?.put(a, b, M) if (ParserATNSimulator.trace_atn_sim) { @@ -536,8 +534,8 @@ public abstract class PredictionContext protected constructor( * * Merge any `equals()` ones. */ - protected fun combineCommonParents(parents: Array) { - val uniqueParents = HashMap() + protected fun combineCommonParents(parents: Array) { + val uniqueParents = HashMap() for (p in parents.indices) { val parent = parents[p] @@ -549,7 +547,7 @@ public abstract class PredictionContext protected constructor( } for (p in parents.indices) { - parents[p] = uniqueParents[parents[p]]!! + parents[p] = uniqueParents[parents[p]] } } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/RuleContext.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/RuleContext.kt index 3e0b1e585..520f420fb 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/RuleContext.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/context/RuleContext.kt @@ -73,7 +73,7 @@ public open class RuleContext : RuleNode { /** * What context invoked this rule? */ - public var parent: RuleContext? = null + private var _parent: RuleContext? = null /** * What state invoked the rule associated with this context? @@ -152,15 +152,15 @@ public open class RuleContext : RuleNode { public constructor() : super() public constructor(parent: RuleContext?, invokingState: Int) : super() { - this.parent = parent + this._parent = parent this.invokingState = invokingState } - override fun readParent(): RuleContext? = - parent + override fun getParent(): RuleContext? = + _parent - override fun assignParent(value: RuleContext?) { - parent = value + override fun setParent(value: RuleContext?) { + _parent = value } public fun depth(): Int { @@ -168,7 +168,7 @@ public open class RuleContext : RuleNode { var p: RuleContext? = this while (p != null) { - p = p.parent + p = p.getParent() n++ } @@ -238,11 +238,11 @@ public open class RuleContext : RuleNode { buf.append(ruleName) } - if (p.parent != null && (ruleNames != null || !p.parent!!.isEmpty)) { + if (p.getParent() != null && (ruleNames != null || !p.getParent()!!.isEmpty)) { buf.append(" ") } - p = p.parent + p = p.getParent() } buf.append("]") diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFA.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFA.kt index 5f9c36efa..6c3de535c 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFA.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFA.kt @@ -24,7 +24,11 @@ public open class DFA( * * Use [Map] so we can get old state back ([Set] only allows you to see if it's there). */ - public val states: MutableMap = HashMap() + private val states: MutableMap = HashMap() + + public fun getStatesMap(): MutableMap { + return states; + } @Volatile public var s0: DFAState? = null @@ -117,7 +121,7 @@ public open class DFA( /** * Return a list of all states in this DFA, ordered by state number. */ - public fun getStates(): List { + public fun getStatesList(): List { val result = ArrayList(states.keys) result.sortBy(DFAState::stateNumber) return result diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFASerializer.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFASerializer.kt index b07402650..5029eb202 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFASerializer.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/dfa/DFASerializer.kt @@ -21,7 +21,7 @@ public open class DFASerializer( } val buf = StringBuilder() - val states = dfa.getStates() + val states = dfa.getStatesList() for (s in states) { var n = 0 diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/DefaultErrorStrategy.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/DefaultErrorStrategy.kt index c94a18729..719337528 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/DefaultErrorStrategy.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/DefaultErrorStrategy.kt @@ -210,7 +210,7 @@ public open class DefaultErrorStrategy : ANTLRErrorStrategy { * functionality by simply overriding this method as a blank { }. */ override fun sync(recognizer: Parser) { - val s = recognizer.interpreter.atn.states[recognizer.state] + val s = recognizer.interpreter!!.atn.states[recognizer.state] // If already recovering, don't try to sync if (inErrorRecoveryMode(recognizer)) { @@ -474,9 +474,9 @@ public open class DefaultErrorStrategy : ANTLRErrorStrategy { // If current token is consistent with what could come after current // ATN state, then we know we're missing a token; error recovery // is free to conjure up and insert the missing token - val currentState = recognizer.interpreter.atn.states[recognizer.state] + val currentState = recognizer.interpreter!!.atn.states[recognizer.state] val next = currentState!!.transition(0).target - val atn = recognizer.interpreter.atn + val atn = recognizer.interpreter!!.atn val expectingAtLL2 = atn.nextTokens(next, recognizer.context) if (expectingAtLL2.contains(currentSymbolType)) { @@ -731,7 +731,7 @@ public open class DefaultErrorStrategy : ANTLRErrorStrategy { * at run-time upon error to avoid overhead during parsing. */ protected open fun getErrorRecoverySet(recognizer: Parser): IntervalSet { - val atn = recognizer.interpreter.atn + val atn = recognizer.interpreter!!.atn var ctx: RuleContext? = recognizer.context val recoverSet = IntervalSet() @@ -741,7 +741,7 @@ public open class DefaultErrorStrategy : ANTLRErrorStrategy { val rt = invokingState!!.transition(0) as RuleTransition val follow = atn.nextTokens(rt.followState) recoverSet.addAll(follow) - ctx = ctx.readParent() + ctx = ctx.getParent() } recoverSet.remove(Token.EPSILON) diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/FailedPredicateException.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/FailedPredicateException.kt index 1573b2593..c3dfe4090 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/FailedPredicateException.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/FailedPredicateException.kt @@ -36,7 +36,7 @@ public class FailedPredicateException( public var predIndex: Int = -1 init { - val s = recognizer.interpreter.atn.states[recognizer.state] + val s = recognizer.interpreter!!.atn.states[recognizer.state] val trans = s!!.transition(0) as AbstractPredicateTransition if (trans is PredicateTransition) { diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/NoViableAltException.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/NoViableAltException.kt index 8565b983a..faa6ef7fd 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/NoViableAltException.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/error/NoViableAltException.kt @@ -33,9 +33,11 @@ public class NoViableAltException( public val startToken: Token? = recognizer.currentToken, offendingToken: Token? = recognizer.currentToken, public val deadEndConfigs: ATNConfigSet? = null, - ctx: ParserRuleContext = recognizer.context!!, + ctx: ParserRuleContext? = recognizer.context, ) : RecognitionException(recognizer, input, ctx) { init { this.offendingToken = offendingToken } + + constructor(recognizer: Parser) : this(recognizer, recognizer.tokenStream, recognizer.currentToken, recognizer.currentToken, null, recognizer.context) } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/info/ParseInfo.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/info/ParseInfo.kt index 89853e197..65882d4fb 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/info/ParseInfo.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/info/ParseInfo.kt @@ -172,6 +172,6 @@ public open class ParseInfo(protected val atnSimulator: ProfilingATNSimulator) { */ public fun getDFASize(decision: Int): Int { val decisionToDFA = atnSimulator.decisionToDFA[decision] - return decisionToDFA.states.size + return decisionToDFA.getStatesMap().size } } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/CharSupport.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/CharSupport.kt new file mode 100644 index 000000000..612c8c498 --- /dev/null +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/CharSupport.kt @@ -0,0 +1,67 @@ +/* + * Copyright (c) 2012-present The ANTLR Project. All rights reserved. + * Use of this file is governed by the BSD 3-clause license that + * can be found in the LICENSE.txt file in the project root. + */ +package org.antlr.v5.runtime.core.misc + +import org.antlr.v5.runtime.core.Lexer + +object CharSupport { + val EscapedCharValue: MutableMap = HashMap() + + val CharValueEscape: MutableMap = HashMap() + + init { + EscapedCharValue['n'] = '\n' + EscapedCharValue['r'] = '\r' + EscapedCharValue['t'] = '\t' + EscapedCharValue['b'] = '\b' + EscapedCharValue['f'] = 0x0C.toChar() + EscapedCharValue['\\'] = '\\' + CharValueEscape['\n'] = "\\n" + CharValueEscape['\r'] = "\\r" + CharValueEscape['\t'] = "\\t" + CharValueEscape['\b'] = "\\b" + CharValueEscape[0x0C.toChar()] = "\\f" + CharValueEscape['\\'] = "\\\\" + } + + fun getPrintable(c: Int): String { + return getPrintable(c, true) + } + + /** Return a string representing the escaped char for code c. E.g., If c + * has value 0x100, you will get "\\u0100". ASCII gets the usual + * char (non-hex) representation. Non-ASCII characters are spit out + * as \\uXXXX or \\u{XXXXXX} escapes. + */ + fun getPrintable(c: Int, appendQuotes: Boolean): String { + val result: String + if (c < Lexer.MIN_CHAR_VALUE) { + result = "" + } else { + val charValueEscape = CharValueEscape[c.toChar()] + result = charValueEscape + ?: if (Character.UnicodeBlock.of(c.toChar()) === Character.UnicodeBlock.BASIC_LATIN && + !Character.isISOControl(c.toChar()) + ) { + if (c == '\\'.code) { + "\\\\" + } else if (c == '\''.code) { + "\\'" + } else { + Character.toString(c.toChar()) + } + } else if (c <= 0xFFFF) { + String.format("\\u%04X", c) + } else { + String.format("\\u{%06X}", c) + } + } + if (appendQuotes) { + return "'$result'" + } + return result + } +} \ No newline at end of file diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntegerList.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntegerList.kt index 3837e5c9e..84ad118f0 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntegerList.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntegerList.kt @@ -156,7 +156,7 @@ public open class IntegerList { if (_size == 0) { EMPTY_DATA } else { - _data.copyOf() + _data.copyOf(_size) } public fun sort() { diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntervalSet.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntervalSet.kt index 001f3952c..df1ce904d 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntervalSet.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntervalSet.kt @@ -509,7 +509,7 @@ public open class IntervalSet : IntSet { buf.append("") } else if (elemAreChar) { buf.append("'") - buf.appendCodePoint(a) + buf.append(CharSupport.getPrintable(a, false)) buf.append("'") } else { buf.append(a) @@ -517,9 +517,9 @@ public open class IntervalSet : IntSet { } else { if (elemAreChar) { buf.append("'") - buf.appendCodePoint(a) + buf.append(CharSupport.getPrintable(a, false)) buf.append("'..'") - buf.appendCodePoint(b) + buf.append(CharSupport.getPrintable(b, false)) buf.append("'") } else { buf.append(a) diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntsEncoder.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntsEncoder.kt new file mode 100644 index 000000000..e473cfdc9 --- /dev/null +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/IntsEncoder.kt @@ -0,0 +1,75 @@ +package org.antlr.v5.runtime.core.misc + + +/** Given a list of integers representing a serialized ATN, encode values too large to fit into 15 bits + * as two 16bit values. We use the high bit (0x8000_0000) to indicate values requiring two 16 bit words. + * If the high bit is set, we grab the next value and combine them to get a 31-bit value. The possible + * input int values are [-1,0x7FFF_FFFF]. + * + * | compression/encoding | uint16 count | type | + * | -------------------------------------------- | ------------ | --------------- | + * | 0xxxxxxx xxxxxxxx | 1 | uint (15 bit) | + * | 1xxxxxxx xxxxxxxx yyyyyyyy yyyyyyyy | 2 | uint (16+ bits) | + * | 11111111 11111111 11111111 11111111 | 2 | int value -1 | + * + * This is only used (other than for testing) by [org.antlr.v4.codegen.model.SerializedJavaATN] + * to encode ints as char values for the java target, but it is convenient to combine it with the + * #decodeIntsEncodedAs16BitWords that follows as they are a pair (I did not want to introduce a new class + * into the runtime). Used only for Java Target. + */ +public fun encodeIntsWith16BitWords(data: IntegerList): IntegerList { + val data16 = IntegerList((data.size() * 1.5).toInt()) + for (i in 0 until data.size()) { + var v = data[i] + if (v == -1) { // use two max uint16 for -1 + data16.add(0xFFFF) + data16.add(0xFFFF) + } else if (v <= 0x7FFF) { + data16.add(v) + } else { // v > 0x7FFF + if (v >= 0x7FFFFFFF) { // too big to fit in 15 bits + 16 bits? (+1 would be 8000_0000 which is bad encoding) + throw UnsupportedOperationException("Serialized ATN data element[$i] = $v doesn't fit in 31 bits") + } + v = v and 0x7FFFFFFF // strip high bit (sentinel) if set + data16.add((v shr 16) or 0x8000) // store high 15-bit word first and set high bit to say word follows + data16.add((v and 0xFFFF)) // then store lower 16-bit word + } + } + return data16 +} + +/** + * Convert a list of chars (16 uint) that represent a serialized and compressed list of ints for an ATN. + */ +public fun decodeIntsEncodedAs16BitWords(data16: CharArray, trimToSize: Boolean = false): IntArray { + // Will be strictly smaller, but we waste bit of space to avoid copying during initialization of parsers + val data = IntArray(data16.size) + var i = 0 + var i2 = 0 + + while (i < data16.size) { + val v = data16[i++] + + if (v.code and 0x8000 == 0) { + // Hi-bit not set? Implies 1-word value + // 7 bit int + data[i2++] = v.code + } else { + // Hi.bit set. Implies 2-word value + val vnext = data16[i++] + + if (v.code == 0xFFFF && vnext.code == 0xFFFF) { // Is it -1? + data[i2++] = -1 + } else { + // 31-bit int + data[i2++] = (v.code and 0x7FFF) shl 16 or (vnext.code and 0xFFFF) + } + } + } + + if (trimToSize) { + return data.copyOf(i2) + } + + return data +} diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/MurmurHash.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/MurmurHash.kt index 595faa7ce..0e71e6058 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/MurmurHash.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/misc/MurmurHash.kt @@ -12,13 +12,21 @@ package org.antlr.v5.runtime.core.misc public object MurmurHash { private const val DEFAULT_SEED = 0 + /** + * Initialize the hash using the default [seed]. + * + * @return The intermediate hash value + */ + public fun initialize(): Int = + DEFAULT_SEED + /** * Initialize the hash using the specified [seed]. * * @param seed The seed * @return The intermediate hash value */ - public fun initialize(seed: Int = DEFAULT_SEED): Int = + public fun initialize(seed: Int): Int = seed /** diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/state/ATNState.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/state/ATNState.kt index f62ea7511..dc75c9ba2 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/state/ATNState.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/state/ATNState.kt @@ -4,6 +4,7 @@ import org.antlr.v5.runtime.core.atn.ATN import org.antlr.v5.runtime.core.misc.IntervalSet import org.antlr.v5.runtime.core.transition.Transition + /** * The following images show the relation of states and * [ATNState.transitions] for various grammar constructs. @@ -64,7 +65,7 @@ public abstract class ATNState { public var atn: ATN? = null public var stateNumber: Int = INVALID_STATE_NUMBER public var ruleIndex: Int = 0 // at runtime, we don't have Rule objects - public var epsilonOnlyTransitions: Boolean = false + public var epsilonOnlyTransitions: Boolean? = null /** * Track the transitions emanating from this ATN state. @@ -94,21 +95,17 @@ public abstract class ATNState { override fun toString(): String = stateNumber.toString() - public fun getTransitions(): Array = + public fun getTransitionsArray(): Array = transitions.toTypedArray() public fun addTransition(e: Transition): Unit = addTransition(transitions.size, e) public fun addTransition(index: Int, e: Transition) { - if (transitions.isEmpty()) { - epsilonOnlyTransitions = e.isEpsilon - } else if (epsilonOnlyTransitions != e.isEpsilon) { - System.err.println("ATN state $stateNumber has both epsilon and non-epsilon transitions.") - epsilonOnlyTransitions = false - } - - var alreadyPresent = false + if(epsilonOnlyTransitions != null && epsilonOnlyTransitions != e.isEpsilon) { + System.err.println("ATN state $stateNumber has both epsilon and non-epsilon transitions.") + } + var alreadyPresent = false for (t in transitions) { if (t.target.stateNumber == e.target.stateNumber) { @@ -124,19 +121,57 @@ public abstract class ATNState { if (!alreadyPresent) { transitions.add(index, e) + recalculateEpsilonOnlyTransitions(); } } public fun transition(i: Int): Transition = transitions[i] - public fun setTransition(i: Int, e: Transition) { - transitions[i] = e + fun getTransitionIndex(transition: Transition?): Int { + return transitions.indexOf(transition) + } + + public fun setTransition(i: Int, e: Transition) { + transitions.removeAt(i); + recalculateEpsilonOnlyTransitions(); + if (epsilonOnlyTransitions != null && epsilonOnlyTransitions != e.isEpsilon) { + System.err.println("ATN state $stateNumber has both epsilon and non-epsilon transitions.\n"); + } + transitions.add(i, e); + recalculateEpsilonOnlyTransitions(); } - public fun removeTransition(index: Int): Transition = - transitions.removeAt(index) + public fun removeTransition(index: Int): Transition { + val result = transitions.removeAt(index) + recalculateEpsilonOnlyTransitions() + return result + } + + public fun removeTransition(transition: Transition): Boolean { + val result = transitions.remove(transition) + recalculateEpsilonOnlyTransitions() + return result + } + + fun findTransition(predicate: java.util.function.Predicate?): Transition? { + return transitions.stream().filter(predicate).findFirst().orElse(null) + } + + + + public fun clearTransitions() { + transitions.clear() + } public fun onlyHasEpsilonTransitions(): Boolean = - epsilonOnlyTransitions + epsilonOnlyTransitions != null && epsilonOnlyTransitions!! + + fun recalculateEpsilonOnlyTransitions() { + if (transitions.size == 0) { + epsilonOnlyTransitions = null + } else { + epsilonOnlyTransitions = transitions.stream().allMatch(Transition::isEpsilon) + } + } } \ No newline at end of file diff --git a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/CodePointTransitions.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/transition/CodePointTransitions.kt similarity index 73% rename from runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/CodePointTransitions.kt rename to runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/transition/CodePointTransitions.kt index b678159d8..f3c56e0c3 100644 --- a/runtime/Kotlin/src/org/antlr/v5/runtime/kotlin/_unused/atn/CodePointTransitions.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/transition/CodePointTransitions.kt @@ -4,12 +4,9 @@ * can be found in the LICENSE.txt file in the project root. */ -package org.antlr.v5.runtime.kotlin._unused.atn +package org.antlr.v5.runtime.core.transition import org.antlr.v5.runtime.core.state.ATNState -import org.antlr.v5.runtime.core.transition.AtomTransition -import org.antlr.v5.runtime.core.transition.RangeTransition -import org.antlr.v5.runtime.core.transition.Transition /** * Utility class to create [AtomTransition], [RangeTransition], @@ -22,13 +19,8 @@ import org.antlr.v5.runtime.core.transition.Transition */ @Suppress("MemberVisibilityCanBePrivate") public object CodePointTransitions { - /** - * Return new [AtomTransition]. - */ - public fun createWithCodePoint(target: ATNState, codePoint: Int): Transition = - createWithCodePointRange(target, codePoint, codePoint) - /** + /** * Return new [AtomTransition] if range represents one atom, else [SetTransition]. */ public fun createWithCodePointRange(target: ATNState, codePointFrom: Int, codePointTo: Int): Transition = diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/ParseTree.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/ParseTree.kt index 359a3dd10..0eedbd978 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/ParseTree.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/ParseTree.kt @@ -41,7 +41,7 @@ public interface ParseTree : SyntaxTree { * * @since 4.7 */ - public fun assignParent(value: RuleContext?) + public fun setParent(value: RuleContext?) /** * The [ParseTreeVisitor] needs a double dispatch method. @@ -55,7 +55,7 @@ public interface ParseTree : SyntaxTree { public fun toStringTree(parser: Parser): String // Narrows down the return type to ParseTree - override fun readParent(): ParseTree? + override fun getParent(): ParseTree? // Narrows down the return type to ParseTree override fun getChild(i: Int): ParseTree? diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/TerminalNodeImpl.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/TerminalNodeImpl.kt index 8472323da..9cc5dc6d8 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/TerminalNodeImpl.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/TerminalNodeImpl.kt @@ -28,10 +28,10 @@ public open class TerminalNodeImpl(override var symbol: Token) : TerminalNode { return Interval(tokenIndex, tokenIndex) } - override fun readParent(): ParseTree? = + override fun getParent(): ParseTree? = parent - override fun assignParent(value: RuleContext?) { + override fun setParent(value: RuleContext?) { parent = value } diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Tree.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Tree.kt index b6d22a643..fa1b7749a 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Tree.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Tree.kt @@ -31,7 +31,7 @@ public interface Tree { * * If the return value is `null`, then this node is the root of the tree. */ - public fun readParent(): Tree? + public fun getParent(): Tree? /** * If there are children, get the `i`th value indexed from `0`. diff --git a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Trees.kt b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Trees.kt index 2651993f4..fcec13289 100644 --- a/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Trees.kt +++ b/runtime/Core/src/main/kotlin/org/antlr/v5/runtime/core/tree/Trees.kt @@ -132,17 +132,17 @@ public object Trees { * @since 4.5.1 */ public fun getAncestors(t: Tree): List { - if (t.readParent() == null) { + if (t.getParent() == null) { return emptyList() } val ancestors = ArrayList() - var t1 = t.readParent() + var t1 = t.getParent() while (t1 != null) { // Insert at start ancestors.add(0, t1) - t1 = t1.readParent() + t1 = t1.getParent() } return ancestors @@ -154,11 +154,11 @@ public object Trees { * @since 4.5.1 */ public fun isAncestorOf(t: Tree?, u: Tree?): Boolean { - if (t == null || u == null || t.readParent() == null) { + if (t == null || u == null || t.getParent() == null) { return false } - var p = u.readParent() + var p = u.getParent() while (p != null) { // Keep reference equality! @@ -166,7 +166,7 @@ public object Trees { return true } - p = p.readParent() + p = p.getParent() } return false diff --git a/runtime/Core/src/test/kotlin/org/antlr/v5/core/misc/CharSupportTest.kt b/runtime/Core/src/test/kotlin/org/antlr/v5/core/misc/CharSupportTest.kt new file mode 100644 index 000000000..72ba2765b --- /dev/null +++ b/runtime/Core/src/test/kotlin/org/antlr/v5/core/misc/CharSupportTest.kt @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2012-present The ANTLR Project. All rights reserved. + * Use of this file is governed by the BSD 3-clause license that + * can be found in the LICENSE.txt file in the project root. + */ +package org.antlr.v5.core.misc + +import org.antlr.v5.runtime.core.misc.CharSupport +import org.antlr.v5.runtime.core.misc.IntervalSet +import org.junit.jupiter.api.Assertions +import org.junit.jupiter.api.Test + +class TestCharSupport { + @Test + fun testGetPrintable() { + Assertions.assertEquals("''", CharSupport.getPrintable(-1)) + Assertions.assertEquals("'\\n'", CharSupport.getPrintable('\n'.code)) + Assertions.assertEquals("'\\\\'", CharSupport.getPrintable('\\'.code)) + Assertions.assertEquals("'\\''", CharSupport.getPrintable('\''.code)) + Assertions.assertEquals("'b'", CharSupport.getPrintable('b'.code)) + Assertions.assertEquals("'\\uFFFF'", CharSupport.getPrintable(0xFFFF)) + Assertions.assertEquals("'\\u{10FFFF}'", CharSupport.getPrintable(0x10FFFF)) + } + + @Test + fun testGetIntervalSetEscapedString() { + Assertions.assertEquals("{}", IntervalSet().toString(true)) + Assertions.assertEquals("'\\u0000'", IntervalSet(0).toString(true)) + Assertions.assertEquals("{'\\u0001'..'\\u0003'}", IntervalSet(3, 1, 2).toString(true)) + } +} \ No newline at end of file diff --git a/runtime/Java/pom.xml b/runtime/Java/pom.xml index 2b241827f..8c00e65ae 100644 --- a/runtime/Java/pom.xml +++ b/runtime/Java/pom.xml @@ -12,7 +12,7 @@ 0.0.1-SNAPSHOT ../../pom.xml - antlr5-runtime + antlr5-java-runtime ANTLR 5 Java Runtime The ANTLR 5 Runtime @@ -23,10 +23,19 @@ dot - 5.9.0 + + org.jetbrains.kotlin + kotlin-stdlib + ${kotlin.version} + + + org.antlr + antlr5-core-runtime + ${project.parent.version} + org.junit.jupiter junit-jupiter-api @@ -126,9 +135,9 @@ maven-compiler-plugin 3.8.1 - 17 - 17 - 17 + ${maven.compiler.release} + ${maven.compiler.source} + ${maven.compiler.target} diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorListener.java b/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorListener.java deleted file mode 100644 index cf6c62a0d..000000000 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorListener.java +++ /dev/null @@ -1,181 +0,0 @@ -/* - * Copyright (c) 2012-present The ANTLR Project. All rights reserved. - * Use of this file is governed by the BSD 3-clause license that - * can be found in the LICENSE.txt file in the project root. - */ - -package org.antlr.v5.runtime; - -import org.antlr.v5.runtime.atn.ATNConfigSet; -import org.antlr.v5.runtime.atn.DecisionInfo; -import org.antlr.v5.runtime.atn.ParserATNSimulator; -import org.antlr.v5.runtime.atn.PredictionMode; -import org.antlr.v5.runtime.dfa.DFA; - -import java.util.BitSet; - -/** How to emit recognition errors. */ -public interface ANTLRErrorListener { - /** - * Upon syntax error, notify any interested parties. This is not how to - * recover from errors or compute error messages. {@link ANTLRErrorStrategy} - * specifies how to recover from syntax errors and how to compute error - * messages. This listener's job is simply to emit a computed message, - * though it has enough information to create its own message in many cases. - * - *

The {@link RecognitionException} is non-null for all syntax errors except - * when we discover mismatched token errors that we can recover from - * in-line, without returning from the surrounding rule (via the single - * token insertion and deletion mechanism).

- * - * @param recognizer - * What parser got the error. From this - * object, you can access the context as well - * as the input stream. - * @param offendingSymbol - * The offending token in the input token - * stream, unless recognizer is a lexer (then it's null). If - * no viable alternative error, {@code e} has token at which we - * started production for the decision. - * @param line - * The line number in the input where the error occurred. - * @param charPositionInLine - * The character position within that line where the error occurred. - * @param msg - * The message to emit. - * @param e - * The exception generated by the parser that led to - * the reporting of an error. It is null in the case where - * the parser was able to recover in line without exiting the - * surrounding rule. - */ - public void syntaxError(Recognizer recognizer, - Object offendingSymbol, - int line, - int charPositionInLine, - String msg, - RecognitionException e); - - /** - * This method is called by the parser when a full-context prediction - * results in an ambiguity. - * - *

Each full-context prediction which does not result in a syntax error - * will call either {@link #reportContextSensitivity} or - * {@link #reportAmbiguity}.

- * - *

When {@code ambigAlts} is not null, it contains the set of potentially - * viable alternatives identified by the prediction algorithm. When - * {@code ambigAlts} is null, use {@link ATNConfigSet#getAlts} to obtain the - * represented alternatives from the {@code configs} argument.

- * - *

When {@code exact} is {@code true}, all of the potentially - * viable alternatives are truly viable, i.e. this is reporting an exact - * ambiguity. When {@code exact} is {@code false}, at least two of - * the potentially viable alternatives are viable for the current input, but - * the prediction algorithm terminated as soon as it determined that at - * least the minimum potentially viable alternative is truly - * viable.

- * - *

When the {@link PredictionMode#LL_EXACT_AMBIG_DETECTION} prediction - * mode is used, the parser is required to identify exact ambiguities so - * {@code exact} will always be {@code true}.

- * - *

This method is not used by lexers.

- * - * @param recognizer the parser instance - * @param dfa the DFA for the current decision - * @param startIndex the input index where the decision started - * @param stopIndex the input input where the ambiguity was identified - * @param exact {@code true} if the ambiguity is exactly known, otherwise - * {@code false}. This is always {@code true} when - * {@link PredictionMode#LL_EXACT_AMBIG_DETECTION} is used. - * @param ambigAlts the potentially ambiguous alternatives, or {@code null} - * to indicate that the potentially ambiguous alternatives are the complete - * set of represented alternatives in {@code configs} - * @param configs the ATN configuration set where the ambiguity was - * identified - */ - void reportAmbiguity(Parser recognizer, - DFA dfa, - int startIndex, - int stopIndex, - boolean exact, - BitSet ambigAlts, - ATNConfigSet configs); - - /** - * This method is called when an SLL conflict occurs and the parser is about - * to use the full context information to make an LL decision. - * - *

If one or more configurations in {@code configs} contains a semantic - * predicate, the predicates are evaluated before this method is called. The - * subset of alternatives which are still viable after predicates are - * evaluated is reported in {@code conflictingAlts}.

- * - *

This method is not used by lexers.

- * - * @param recognizer the parser instance - * @param dfa the DFA for the current decision - * @param startIndex the input index where the decision started - * @param stopIndex the input index where the SLL conflict occurred - * @param conflictingAlts The specific conflicting alternatives. If this is - * {@code null}, the conflicting alternatives are all alternatives - * represented in {@code configs}. At the moment, conflictingAlts is non-null - * (for the reference implementation, but Sam's optimized version can see this - * as null). - * @param configs the ATN configuration set where the SLL conflict was - * detected - */ - void reportAttemptingFullContext(Parser recognizer, - DFA dfa, - int startIndex, - int stopIndex, - BitSet conflictingAlts, - ATNConfigSet configs); - - /** - * This method is called by the parser when a full-context prediction has a - * unique result. - * - *

Each full-context prediction which does not result in a syntax error - * will call either {@link #reportContextSensitivity} or - * {@link #reportAmbiguity}.

- * - *

For prediction implementations that only evaluate full-context - * predictions when an SLL conflict is found (including the default - * {@link ParserATNSimulator} implementation), this method reports cases - * where SLL conflicts were resolved to unique full-context predictions, - * i.e. the decision was context-sensitive. This report does not necessarily - * indicate a problem, and it may appear even in completely unambiguous - * grammars.

- * - *

{@code configs} may have more than one represented alternative if the - * full-context prediction algorithm does not evaluate predicates before - * beginning the full-context prediction. In all cases, the final prediction - * is passed as the {@code prediction} argument.

- * - *

Note that the definition of "context sensitivity" in this method - * differs from the concept in {@link DecisionInfo#contextSensitivities}. - * This method reports all instances where an SLL conflict occurred but LL - * parsing produced a unique result, whether or not that unique result - * matches the minimum alternative in the SLL conflicting set.

- * - *

This method is not used by lexers.

- * - * @param recognizer the parser instance - * @param dfa the DFA for the current decision - * @param startIndex the input index where the decision started - * @param stopIndex the input index where the context sensitivity was - * finally determined - * @param prediction the unambiguous result of the full-context prediction - * @param configs the ATN configuration set where the unambiguous prediction - * was determined - */ - void reportContextSensitivity(Parser recognizer, - DFA dfa, - int startIndex, - int stopIndex, - int prediction, - ATNConfigSet configs); -} diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorStrategy.java b/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorStrategy.java deleted file mode 100644 index 5f5321556..000000000 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/ANTLRErrorStrategy.java +++ /dev/null @@ -1,120 +0,0 @@ -/* - * Copyright (c) 2012-present The ANTLR Project. All rights reserved. - * Use of this file is governed by the BSD 3-clause license that - * can be found in the LICENSE.txt file in the project root. - */ - -package org.antlr.v5.runtime; - -import org.antlr.v5.runtime.tree.ErrorNode; - -/** - * The interface for defining strategies to deal with syntax errors encountered - * during a parse by ANTLR-generated parsers. We distinguish between three - * different kinds of errors: - * - *
    - *
  • The parser could not figure out which path to take in the ATN (none of - * the available alternatives could possibly match)
  • - *
  • The current input does not match what we were looking for
  • - *
  • A predicate evaluated to false
  • - *
- * - * Implementations of this interface report syntax errors by calling - * {@link Parser#notifyErrorListeners}. - * - *

TODO: what to do about lexers

- */ -public interface ANTLRErrorStrategy { - /** - * Reset the error handler state for the specified {@code recognizer}. - * @param recognizer the parser instance - */ - void reset(Parser recognizer); - - /** - * This method is called when an unexpected symbol is encountered during an - * inline match operation, such as {@link Parser#match}. If the error - * strategy successfully recovers from the match failure, this method - * returns the {@link Token} instance which should be treated as the - * successful result of the match. - * - *

This method handles the consumption of any tokens - the caller should - * not call {@link Parser#consume} after a successful recovery.

- * - *

Note that the calling code will not report an error if this method - * returns successfully. The error strategy implementation is responsible - * for calling {@link Parser#notifyErrorListeners} as appropriate.

- * - * @param recognizer the parser instance - * @throws RecognitionException if the error strategy was not able to - * recover from the unexpected input symbol - */ - Token recoverInline(Parser recognizer) throws RecognitionException; - - /** - * This method is called to recover from exception {@code e}. This method is - * called after {@link #reportError} by the default exception handler - * generated for a rule method. - * - * @see #reportError - * - * @param recognizer the parser instance - * @param e the recognition exception to recover from - * @throws RecognitionException if the error strategy could not recover from - * the recognition exception - */ - void recover(Parser recognizer, RecognitionException e) throws RecognitionException; - - /** - * This method provides the error handler with an opportunity to handle - * syntactic or semantic errors in the input stream before they result in a - * {@link RecognitionException}. - * - *

The generated code currently contains calls to {@link #sync} after - * entering the decision state of a closure block ({@code (...)*} or - * {@code (...)+}).

- * - *

For an implementation based on Jim Idle's "magic sync" mechanism, see - * {@link DefaultErrorStrategy#sync}.

- * - * @see DefaultErrorStrategy#sync - * - * @param recognizer the parser instance - * @throws RecognitionException if an error is detected by the error - * strategy but cannot be automatically recovered at the current state in - * the parsing process - */ - void sync(Parser recognizer) throws RecognitionException; - - /** - * Tests whether or not {@code recognizer} is in the process of recovering - * from an error. In error recovery mode, {@link Parser#consume} adds - * symbols to the parse tree by calling - * {@link Parser#createErrorNode(ParserRuleContext, Token)} then - * {@link ParserRuleContext#addErrorNode(ErrorNode)} instead of - * {@link Parser#createTerminalNode(ParserRuleContext, Token)}. - * - * @param recognizer the parser instance - * @return {@code true} if the parser is currently recovering from a parse - * error, otherwise {@code false} - */ - boolean inErrorRecoveryMode(Parser recognizer); - - /** - * This method is called by when the parser successfully matches an input - * symbol. - * - * @param recognizer the parser instance - */ - void reportMatch(Parser recognizer); - - /** - * Report any kind of {@link RecognitionException}. This method is called by - * the default exception handler generated for a rule method. - * - * @param recognizer the parser instance - * @param e the recognition exception to report - */ - void reportError(Parser recognizer, RecognitionException e); -} diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/BailErrorStrategy.java b/runtime/Java/src/main/java/org/antlr/v5/runtime/BailErrorStrategy.java index e977e19b1..9cf1fca87 100644 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/BailErrorStrategy.java +++ b/runtime/Java/src/main/java/org/antlr/v5/runtime/BailErrorStrategy.java @@ -6,13 +6,20 @@ package org.antlr.v5.runtime; -import org.antlr.v5.runtime.misc.ParseCancellationException; +import org.antlr.v5.runtime.core.Parser; +import org.antlr.v5.runtime.core.Token; +import org.antlr.v5.runtime.core.context.ParserRuleContext; +import org.antlr.v5.runtime.core.error.ANTLRErrorStrategy; +import org.antlr.v5.runtime.core.error.DefaultErrorStrategy; +import org.antlr.v5.runtime.core.error.InputMismatchException; +import org.antlr.v5.runtime.core.error.RecognitionException; +import org.antlr.v5.runtime.core.misc.ParseCancellationException; /** * This implementation of {@link ANTLRErrorStrategy} responds to syntax errors * by immediately canceling the parse operation with a * {@link ParseCancellationException}. The implementation ensures that the - * {@link ParserRuleContext#exception} field is set for all parse tree nodes + * {@link ParserRuleContext#getException} field is set for all parse tree nodes * that were not completed prior to encountering the error. * *

@@ -44,8 +51,8 @@ public class BailErrorStrategy extends DefaultErrorStrategy { */ @Override public void recover(Parser recognizer, RecognitionException e) { - for (ParserRuleContext context = recognizer.getContext(); context != null; context = context.getParent()) { - context.exception = e; + for (ParserRuleContext context = recognizer.getContext(); context != null; context = (ParserRuleContext) context.getParent()) { + context.setException(e); } throw new ParseCancellationException(e); @@ -59,8 +66,8 @@ public Token recoverInline(Parser recognizer) throws RecognitionException { InputMismatchException e = new InputMismatchException(recognizer); - for (ParserRuleContext context = recognizer.getContext(); context != null; context = context.getParent()) { - context.exception = e; + for (ParserRuleContext context = recognizer.getContext(); context != null; context = (ParserRuleContext) context.getParent()) { + context.setException(e); } throw new ParseCancellationException(e); diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/BaseErrorListener.java b/runtime/Java/src/main/java/org/antlr/v5/runtime/BaseErrorListener.java index 23fb70b3a..85babb76a 100644 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/BaseErrorListener.java +++ b/runtime/Java/src/main/java/org/antlr/v5/runtime/BaseErrorListener.java @@ -5,8 +5,13 @@ */ package org.antlr.v5.runtime; -import org.antlr.v5.runtime.atn.ATNConfigSet; -import org.antlr.v5.runtime.dfa.DFA; +import org.antlr.v5.runtime.core.atn.ATNConfigSet; +import org.antlr.v5.runtime.core.Parser; +import org.antlr.v5.runtime.core.Recognizer; +import org.antlr.v5.runtime.core.error.ANTLRErrorListener; +import org.antlr.v5.runtime.core.error.RecognitionException; +import org.antlr.v5.runtime.core.dfa.DFA; +import org.jetbrains.annotations.NotNull; import java.util.BitSet; @@ -19,7 +24,7 @@ */ public class BaseErrorListener implements ANTLRErrorListener { @Override - public void syntaxError(Recognizer recognizer, + public void syntaxError(@NotNull Recognizer recognizer, Object offendingSymbol, int line, int charPositionInLine, diff --git a/runtime/Java/src/main/java/org/antlr/v5/runtime/BufferedTokenStream.java b/runtime/Java/src/main/java/org/antlr/v5/runtime/BufferedTokenStream.java deleted file mode 100644 index 4e066605b..000000000 --- a/runtime/Java/src/main/java/org/antlr/v5/runtime/BufferedTokenStream.java +++ /dev/null @@ -1,491 +0,0 @@ -/* - * Copyright (c) 2012-present The ANTLR Project. All rights reserved. - * Use of this file is governed by the BSD 3-clause license that - * can be found in the LICENSE.txt file in the project root. - */ - -package org.antlr.v5.runtime; - -import org.antlr.v5.runtime.misc.Interval; - -import java.util.ArrayList; -import java.util.HashSet; -import java.util.List; -import java.util.Set; - -/** - * This implementation of {@link TokenStream} loads tokens from a - * {@link TokenSource} on-demand, and places the tokens in a buffer to provide - * access to any previous token by index. - * - *

- * This token stream ignores the value of {@link Token#getChannel}. If your - * parser requires the token stream filter tokens to only those on a particular - * channel, such as {@link Token#DEFAULT_CHANNEL} or - * {@link Token#HIDDEN_CHANNEL}, use a filtering token stream such a - * {@link CommonTokenStream}.

- */ -public class BufferedTokenStream implements TokenStream { - /** - * The {@link TokenSource} from which tokens for this stream are fetched. - */ - protected TokenSource tokenSource; - - /** - * A collection of all tokens fetched from the token source. The list is - * considered a complete view of the input once {@link #fetchedEOF} is set - * to {@code true}. - */ - protected List tokens = new ArrayList(100); - - /** - * The index into {@link #tokens} of the current token (next token to - * {@link #consume}). {@link #tokens}{@code [}{@link #p}{@code ]} should be - * {@link #LT LT(1)}. - * - *

This field is set to -1 when the stream is first constructed or when - * {@link #setTokenSource} is called, indicating that the first token has - * not yet been fetched from the token source. For additional information, - * see the documentation of {@link IntStream} for a description of - * Initializing Methods.

- */ - protected int p = -1; - - /** - * Indicates whether the {@link Token#EOF} token has been fetched from - * {@link #tokenSource} and added to {@link #tokens}. This field improves - * performance for the following cases: - * - *