forked from jasder/antlr
Merge branch 'master' into Issue_1666
This commit is contained in:
commit
1341d35f37
|
@ -31,6 +31,9 @@ __pycache__/
|
||||||
|
|
||||||
# User-specific files (MonoDevelop/Xamarin Studio)
|
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||||
*.userprefs
|
*.userprefs
|
||||||
|
*.user
|
||||||
|
.vs/
|
||||||
|
project.lock.json
|
||||||
|
|
||||||
# Build results
|
# Build results
|
||||||
[Dd]ebug/
|
[Dd]ebug/
|
||||||
|
|
10
.travis.yml
10
.travis.yml
|
@ -45,12 +45,22 @@ matrix:
|
||||||
- os: linux
|
- os: linux
|
||||||
jdk: oraclejdk7
|
jdk: oraclejdk7
|
||||||
env: TARGET=csharp
|
env: TARGET=csharp
|
||||||
|
- os: linux
|
||||||
|
jdk: oraclejdk7
|
||||||
|
dist: trusty
|
||||||
|
env: TARGET=dotnet
|
||||||
- os: linux
|
- os: linux
|
||||||
jdk: oraclejdk7
|
jdk: oraclejdk7
|
||||||
env: TARGET=python2
|
env: TARGET=python2
|
||||||
- os: linux
|
- os: linux
|
||||||
jdk: oraclejdk7
|
jdk: oraclejdk7
|
||||||
env: TARGET=python3
|
env: TARGET=python3
|
||||||
|
addons:
|
||||||
|
apt:
|
||||||
|
sources:
|
||||||
|
- deadsnakes # source required so it finds the package definition below
|
||||||
|
packages:
|
||||||
|
- python3.5
|
||||||
- os: linux
|
- os: linux
|
||||||
jdk: oraclejdk7
|
jdk: oraclejdk7
|
||||||
env: TARGET=javascript
|
env: TARGET=javascript
|
||||||
|
|
|
@ -3,6 +3,4 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
|
|
|
@ -3,8 +3,6 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
echo "deb http://download.mono-project.com/repo/debian wheezy/snapshots/3.12.1 main" | sudo tee /etc/apt/sources.list.d/mono-xamarin.list
|
echo "deb http://download.mono-project.com/repo/debian wheezy/snapshots/3.12.1 main" | sudo tee /etc/apt/sources.list.d/mono-xamarin.list
|
||||||
sudo apt-get install -qq mono-complete
|
sudo apt-get install -qq mono-complete
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
# install dotnet
|
||||||
|
sudo sh -c 'echo "deb [arch=amd64] https://apt-mo.trafficmanager.net/repos/dotnet-release/ trusty main" > /etc/apt/sources.list.d/dotnetdev.list'
|
||||||
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 417A0893
|
||||||
|
sudo apt-get update
|
||||||
|
|
||||||
|
sudo apt-get install dotnet-dev-1.0.0-preview2.1-003177
|
||||||
|
|
||||||
|
# install mvn
|
||||||
|
wget http://apache.mirrors.lucidnetworks.net/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz && \
|
||||||
|
wget https://www.apache.org/dist/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz.md5 && \
|
||||||
|
echo "$(cat apache-maven-3.3.9-bin.tar.gz.md5) apache-maven-3.3.9-bin.tar.gz" > apache-maven-3.3.9-bin.tar.gz.md5 && \
|
||||||
|
md5sum -c *.md5
|
||||||
|
|
||||||
|
sudo rm -rf /usr/local/maven/ && sudo mkdir -p /usr/local/maven && \
|
||||||
|
sudo tar xzvf apache-maven-3.3.9-bin.tar.gz -C /usr/local/maven --strip-components=1
|
||||||
|
|
||||||
|
mvn -v
|
||||||
|
|
|
@ -3,8 +3,6 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
eval "$(sudo gimme 1.7.3)"
|
eval "$(sudo gimme 1.7.3)"
|
||||||
( go version ; go env ) || true
|
( go version ; go env ) || true
|
||||||
|
|
|
@ -3,6 +3,4 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
|
curl -sL https://deb.nodesource.com/setup_0.12 | sudo -E bash -
|
||||||
sudo apt-get install -qq nodejs
|
sudo apt-get install -qq nodejs
|
||||||
|
node --version
|
||||||
|
|
|
@ -3,7 +3,5 @@
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
sudo apt-get update -qq
|
||||||
python --version
|
python --version
|
||||||
|
|
|
@ -2,9 +2,4 @@
|
||||||
|
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF
|
|
||||||
sudo add-apt-repository ppa:fkrull/deadsnakes -y
|
|
||||||
sudo add-apt-repository ppa:rwky/nodejs -y
|
|
||||||
sudo apt-get update -qq
|
|
||||||
sudo apt-get install -qq python3.5
|
|
||||||
python3 --version
|
python3 --version
|
||||||
|
|
|
@ -0,0 +1,4 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
mvn -q -Dparallel=methods -DthreadCount=4 -Dtest=csharp.* -DargLine="-Dantlr-csharp-netstandard=true" test
|
||||||
|
|
|
@ -0,0 +1,10 @@
|
||||||
|
# Contributing to ANTLR 4
|
||||||
|
|
||||||
|
1. [Fork](https://help.github.com/articles/fork-a-repo) the [antlr/antlr4 repo](https://github.com/antlr/antlr4)
|
||||||
|
2. Install and configure [EditorConfig](http://editorconfig.org/) so your text editor or IDE uses the ANTLR 4 coding style
|
||||||
|
3. [Build ANTLR 4](doc/building-antlr.md)
|
||||||
|
4. [Run the ANTLR project unit tests](doc/antlr-project-testing.md)
|
||||||
|
5. Create a [pull request](https://help.github.com/articles/using-pull-requests/) including your change
|
||||||
|
|
||||||
|
|
||||||
|
**Note:** You must sign the `contributors.txt` certificate of origin with your pull request if you've not done so before.
|
26
LICENSE.txt
26
LICENSE.txt
|
@ -24,3 +24,29 @@ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
=====
|
||||||
|
|
||||||
|
MIT License for codepointat.js from https://git.io/codepointat
|
||||||
|
MIT License for fromcodepoint.js from https://git.io/vDW1m
|
||||||
|
|
||||||
|
Copyright Mathias Bynens <https://mathiasbynens.be/>
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining
|
||||||
|
a copy of this software and associated documentation files (the
|
||||||
|
"Software"), to deal in the Software without restriction, including
|
||||||
|
without limitation the rights to use, copy, modify, merge, publish,
|
||||||
|
distribute, sublicense, and/or sell copies of the Software, and to
|
||||||
|
permit persons to whom the Software is furnished to do so, subject to
|
||||||
|
the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be
|
||||||
|
included in all copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
|
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||||
|
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||||
|
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||||
|
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.antlr</groupId>
|
<groupId>org.antlr</groupId>
|
||||||
<artifactId>antlr4-master</artifactId>
|
<artifactId>antlr4-master</artifactId>
|
||||||
<version>4.6</version>
|
<version>4.6.1-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<artifactId>antlr4-maven-plugin</artifactId>
|
<artifactId>antlr4-maven-plugin</artifactId>
|
||||||
<packaging>maven-plugin</packaging>
|
<packaging>maven-plugin</packaging>
|
||||||
|
|
|
@ -150,6 +150,13 @@ public class Antlr4Mojo extends AbstractMojo {
|
||||||
@Parameter(property = "project", required = true, readonly = true)
|
@Parameter(property = "project", required = true, readonly = true)
|
||||||
protected MavenProject project;
|
protected MavenProject project;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Specifies whether sources are added to the {@code compile} or
|
||||||
|
* {@code test} scope.
|
||||||
|
*/
|
||||||
|
@Parameter(property = "antlr4.generateTestSources", defaultValue = "false")
|
||||||
|
private boolean generateTestSources;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The directory where the ANTLR grammar files ({@code *.g4}) are located.
|
* The directory where the ANTLR grammar files ({@code *.g4}) are located.
|
||||||
*/
|
*/
|
||||||
|
@ -190,7 +197,12 @@ public class Antlr4Mojo extends AbstractMojo {
|
||||||
}
|
}
|
||||||
|
|
||||||
void addSourceRoot(File outputDir) {
|
void addSourceRoot(File outputDir) {
|
||||||
project.addCompileSourceRoot(outputDir.getPath());
|
if (generateTestSources) {
|
||||||
|
project.addTestCompileSourceRoot(outputDir.getPath());
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
project.addCompileSourceRoot(outputDir.getPath());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -127,4 +127,14 @@ YYYY/MM/DD, github id, Full name, email
|
||||||
2016/12/01, samtatasurya, Samuel Tatasurya, xemradiant@gmail.com
|
2016/12/01, samtatasurya, Samuel Tatasurya, xemradiant@gmail.com
|
||||||
2016/12/03, redxdev, Samuel Bloomberg, sam@redxdev.com
|
2016/12/03, redxdev, Samuel Bloomberg, sam@redxdev.com
|
||||||
2016/12/11, Gaulouis, Gaulouis, gaulouis.com@gmail.com
|
2016/12/11, Gaulouis, Gaulouis, gaulouis.com@gmail.com
|
||||||
|
2016/12/22, akosthekiss, Akos Kiss, akiss@inf.u-szeged.hu
|
||||||
|
2016/12/24, adrpo, Adrian Pop, adrian.pop@liu.se
|
||||||
|
2017/01/11, robertbrignull, Robert Brignull, robertbrignull@gmail.com
|
||||||
|
2017/01/13, marcelo-rocha, Marcelo Rocha, mcrocha@gmail.com
|
||||||
|
2017/01/23, bhamiltoncx, Ben Hamilton, bhamiltoncx+antlr@gmail.com
|
||||||
|
2017/01/18, mshockwave, Bekket McClane, yihshyng223@gmail.com
|
||||||
|
2017/02/10, lionelplessis, Lionel Plessis, lionelplessis@users.noreply.github.com
|
||||||
|
2017/02/14, lecode-official, David Neumann, david.neumann@lecode.de
|
||||||
|
2017/02/14, xied75, Dong Xie, xied75@gmail.com
|
||||||
2017/02/20, Thomasb81, Thomas Burg, thomasb81@gmail.com
|
2017/02/20, Thomasb81, Thomas Burg, thomasb81@gmail.com
|
||||||
|
|
||||||
|
|
|
@ -174,13 +174,20 @@ At this point, you should have an editor which displays an error icon next to th
|
||||||
|
|
||||||
What remains to be done is have our validate function actually validate the input. Finally ANTLR comes in the picture!
|
What remains to be done is have our validate function actually validate the input. Finally ANTLR comes in the picture!
|
||||||
|
|
||||||
To start with, let's load ANTLR and your parser, listener etc.. Easy, since you could write:
|
To start with, let's load ANTLR and your parser, listener etc..
|
||||||
|
|
||||||
|
The preferred approach for loading parser code is to bundle your parser, [as described here](javascript-target.md).
|
||||||
|
You can then load it as part of the importScripts instruction at the start of your worker code.
|
||||||
|
|
||||||
|
Another approach is to load it using 'require'. Easy, since you could write:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
var antlr4 = require('antlr4/index');
|
var antlr4 = require('antlr4/index');
|
||||||
```
|
```
|
||||||
|
|
||||||
This may work, but it's actually unreliable. The reason is that the require function used by ANTLR, which exactly mimics the NodeJS require function, uses a different syntax than the require function that comes with ACE. So we need to bring in a require function that conforms to the NodeJS syntax. I personally use one that comes from Torben Haase's Honey project, which you can find here. But hey, now we're going to have 2 'require' functions not compatible with each other! Indeed, this is why you need to take special care, as follows:
|
This may work, but it's actually unreliable. The reason is that the 'require' function that comes with ACE uses a different syntax than the 'require' function used by ANTLR, which follows the NodeJS 'require' convention.
|
||||||
|
So we need to bring in a NodeJS compatible 'require' function that conforms to the NodeJS syntax. I personally use one that comes from Torben Haase's Honey project, which you can find in li/require.js.
|
||||||
|
But hey, now we're going to have 2 'require' functions not compatible with each other! Indeed, this is why you need to take special care, as follows:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
// load nodejs compatible require
|
// load nodejs compatible require
|
||||||
|
@ -191,7 +198,8 @@ importScripts("../lib/require.js");
|
||||||
var antlr4_require = require;
|
var antlr4_require = require;
|
||||||
require = ace_require;
|
require = ace_require;
|
||||||
```
|
```
|
||||||
Now it's safe to load antlr, and the parsers generated for your language. Assuming that your language files (generated or hand-built) are in a folder with an index.js file that calls require for each file, your parser loading code can be as simple as follows:
|
Now it's safe to load antlr and the parsers generated for your language.
|
||||||
|
Assuming that your language files (generated or hand-built) are in a folder with an index.js file that calls require for each file, your parser loading code can be as simple as follows:
|
||||||
```js
|
```js
|
||||||
// load antlr4 and myLanguage
|
// load antlr4 and myLanguage
|
||||||
var antlr4, mylanguage;
|
var antlr4, mylanguage;
|
||||||
|
@ -204,6 +212,7 @@ try {
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
Please note the try-finally construct. ANTLR uses 'require' synchronously so it's perfectly safe to ignore the ACE 'require' while running ANTLR code. ACE itself does not guarantee synchronous execution, so you are much safer always switching 'require' back to 'ace_require'.
|
Please note the try-finally construct. ANTLR uses 'require' synchronously so it's perfectly safe to ignore the ACE 'require' while running ANTLR code. ACE itself does not guarantee synchronous execution, so you are much safer always switching 'require' back to 'ace_require'.
|
||||||
|
|
||||||
Now detecting deep syntax errors in your code is a task for your ANTLR listener or visitor or whatever piece of code you've delegated this to. We're not going to describe this here, since it would require some knowledge of your language. However, detecting grammar syntax errors is something ANTLR does beautifully (isn't that why you went for ANTLR in the first place?). So what we will illustrate here is how to report grammar syntax errors. I have no doubt that from there, you will be able to extend the validator to suit your specific needs.
|
Now detecting deep syntax errors in your code is a task for your ANTLR listener or visitor or whatever piece of code you've delegated this to. We're not going to describe this here, since it would require some knowledge of your language. However, detecting grammar syntax errors is something ANTLR does beautifully (isn't that why you went for ANTLR in the first place?). So what we will illustrate here is how to report grammar syntax errors. I have no doubt that from there, you will be able to extend the validator to suit your specific needs.
|
||||||
Whenever ANTLR encounters an unexpected token, it fires an error. By default, the error is routed to an error listener which simply writes to the console.
|
Whenever ANTLR encounters an unexpected token, it fires an error. By default, the error is routed to an error listener which simply writes to the console.
|
||||||
What we need to do is replace this listener by our own listener, se we can route errors to the ACE editor. First, let's create such a listener:
|
What we need to do is replace this listener by our own listener, se we can route errors to the ACE editor. First, let's create such a listener:
|
||||||
|
@ -243,5 +252,4 @@ var validate = function(input) {
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
You know what? That's it! You now have an ACE editor that does syntax validation using ANTLR! I hope you find this useful, and simple enough to get started.
|
You know what? That's it! You now have an ACE editor that does syntax validation using ANTLR! I hope you find this useful, and simple enough to get started.
|
||||||
What I did not address here is packaging, not something I'm an expert at. The good news is that it makes development simple, since I don't have to run any compilation process. I just edit my code, reload my editor page, and check how it goes.
|
WNow wait, hey! How do you debug this? Well, as usual, using Chrome, since no other browser is able to debug worker code. What a shame...
|
||||||
Now wait, hey! How do you debug this? Well, as usual, using Chrome, since neither Firefox or Safari are able to debug worker code. What a shame...
|
|
||||||
|
|
|
@ -79,15 +79,10 @@ This example assumes your grammar contains a parser rule named `key` for which t
|
||||||
There are a couple of things that only the C++ ANTLR target has to deal with. They are described here.
|
There are a couple of things that only the C++ ANTLR target has to deal with. They are described here.
|
||||||
|
|
||||||
### Build Aspects
|
### Build Aspects
|
||||||
|
The code generation (by running the ANTLR4 jar) allows to specify 2 values you might find useful for better integration of the generated files into your application (both are optional):
|
||||||
The code generation (by running the ANTLR4 jar) allows to specify 2 values you
|
|
||||||
might find useful for better integration of the generated files into your
|
|
||||||
application (both are optional):
|
|
||||||
|
|
||||||
* A **namespace**: use the **`-package`** parameter to specify the namespace you want.
|
* A **namespace**: use the **`-package`** parameter to specify the namespace you want.
|
||||||
* An **export macro**: especially in VC++ extra work is required to export your classes from a DLL.
|
* An **export macro**: especially in VC++ extra work is required to export your classes from a DLL. This is usually accomplished by a macro that has different values depending on whether you are creating the DLL or import it. The ANTLR4 runtime itself also uses one for its classes:
|
||||||
This is usually accomplished by a macro that has different values depending on whether
|
|
||||||
you are creating the DLL or import it. The ANTLR4 runtime itself also uses one for its classes:
|
|
||||||
|
|
||||||
```c++
|
```c++
|
||||||
#ifdef ANTLR4CPP_EXPORTS
|
#ifdef ANTLR4CPP_EXPORTS
|
||||||
|
@ -100,30 +95,17 @@ you are creating the DLL or import it. The ANTLR4 runtime itself also uses one f
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
```
|
```
|
||||||
|
Just like the `ANTLR4CPP_PUBLIC` macro here you can specify your own one for the generated classes using the **`-DexportMacro=...`** command-line parameter or
|
||||||
Just like the `ANTLR4CPP_PUBLIC` macro here you can specify your own one for
|
|
||||||
the generated classes using the **`-DexportMacro=...`** command-line parameter or
|
|
||||||
grammar option `options {exportMacro='...';}` in your grammar file.
|
grammar option `options {exportMacro='...';}` in your grammar file.
|
||||||
|
|
||||||
In order to create a static lib in Visual Studio define the `ANTLR4CPP_STATIC` macro
|
In order to create a static lib in Visual Studio define the `ANTLR4CPP_STATIC` macro in addition to the project settings that must be set for a static library (if you compile the runtime yourself).
|
||||||
in addition to the project settings that must be set for a static library
|
|
||||||
(if you compile the runtime yourself).
|
|
||||||
|
|
||||||
For gcc and clang it is possible to use the `-fvisibility=hidden` setting to
|
For gcc and clang it is possible to use the `-fvisibility=hidden` setting to hide all symbols except those that are made default-visible (which has been defined for all public classes in the runtime).
|
||||||
hide all symbols except those that are made default-visible (which has been
|
|
||||||
defined for all public classes in the runtime).
|
|
||||||
|
|
||||||
### Memory Management
|
### Memory Management
|
||||||
|
Since C++ has no built-in memory management we need to take extra care. For that we rely mostly on smart pointers, which however might cause time penalties or memory side effects (like cyclic references) if not used with care. Currently however the memory household looks very stable. Generally, when you see a raw pointer in code consider this as being managed elsewehere. You should never try to manage such a pointer (delete, assign to smart pointer etc.).
|
||||||
Since C++ has no built-in memory management we need to take extra care.
|
|
||||||
For that we rely mostly on smart pointers, which however might cause time
|
|
||||||
penalties or memory side effects (like cyclic references) if not used with care.
|
|
||||||
Currently however the memory household looks very stable. Generally, when you
|
|
||||||
see a raw pointer in code consider this as being managed elsewehere. You
|
|
||||||
should never try to manage such a pointer (delete, assign to smart pointer etc.).
|
|
||||||
|
|
||||||
### Unicode Support
|
### Unicode Support
|
||||||
|
|
||||||
Encoding is mostly an input issue, i.e. when the lexer converts text input into lexer tokens. The parser is completely encoding unaware. However, lexer input in the grammar is defined by character ranges with either a single member (e.g. 'a' or [a] or [abc]), an explicit range (e.g. 'a'..'z' or [a-z]), the full Unicode range (for a wildcard) and the full Unicode range minus a sub range (for negated ranges, e.g. ~[a]). The explicit ranges (including single member ranges) are encoded in the serialized ATN by 16bit numbers, hence cannot reach beyond 0xFFFF (the Unicode BMP), while the implicit ranges can include any value (and hence support the full Unicode set, up to 0x10FFFF).
|
Encoding is mostly an input issue, i.e. when the lexer converts text input into lexer tokens. The parser is completely encoding unaware. However, lexer input in the grammar is defined by character ranges with either a single member (e.g. 'a' or [a] or [abc]), an explicit range (e.g. 'a'..'z' or [a-z]), the full Unicode range (for a wildcard) and the full Unicode range minus a sub range (for negated ranges, e.g. ~[a]). The explicit ranges (including single member ranges) are encoded in the serialized ATN by 16bit numbers, hence cannot reach beyond 0xFFFF (the Unicode BMP), while the implicit ranges can include any value (and hence support the full Unicode set, up to 0x10FFFF).
|
||||||
|
|
||||||
> An interesting side note here is that the Java target fully supports Unicode as well, despite the inherent limitations from the serialized ATN. That's possible because the Java String class represents characters beyond the BMP as surrogate pairs (two 16bit values) and even reads them as 2 separate input characters. To make this work a character range for an identifier in a grammar must include the surrogate pairs area (for a Java parser).
|
> An interesting side note here is that the Java target fully supports Unicode as well, despite the inherent limitations from the serialized ATN. That's possible because the Java String class represents characters beyond the BMP as surrogate pairs (two 16bit values) and even reads them as 2 separate input characters. To make this work a character range for an identifier in a grammar must include the surrogate pairs area (for a Java parser).
|
||||||
|
@ -133,7 +115,6 @@ The C++ target however always expects UTF-8 input (either in a string or via a w
|
||||||
The differences in handling characters beyond the BMP leads to a difference between Java and C++ lexers: the character offsets may not concur. This is because Java reads two 16bit values per Unicode char (if that falls into the surrogate area) while a C++ parser only reads one 32bit value. That usually doesn't have practical consequences, but might confuse people when comparing token positions.
|
The differences in handling characters beyond the BMP leads to a difference between Java and C++ lexers: the character offsets may not concur. This is because Java reads two 16bit values per Unicode char (if that falls into the surrogate area) while a C++ parser only reads one 32bit value. That usually doesn't have practical consequences, but might confuse people when comparing token positions.
|
||||||
|
|
||||||
### Named Actions
|
### Named Actions
|
||||||
|
|
||||||
In order to help customizing the generated files there are a number of additional socalled **named actions**. These actions are tight to specific areas in the generated code and allow to add custom (target specific) code. All targets support these actions
|
In order to help customizing the generated files there are a number of additional socalled **named actions**. These actions are tight to specific areas in the generated code and allow to add custom (target specific) code. All targets support these actions
|
||||||
|
|
||||||
* @parser::header
|
* @parser::header
|
||||||
|
|
|
@ -16,7 +16,7 @@ Links in the documentation refer to various sections of the book but have been r
|
||||||
<a href=""><img src=images/tpantlr2.png width=120></a>
|
<a href=""><img src=images/tpantlr2.png width=120></a>
|
||||||
<a href=""><img src=images/tpdsl.png width=120></a>
|
<a href=""><img src=images/tpdsl.png width=120></a>
|
||||||
<a href="https://www.youtube.com/watch?v=OAoA3E-cyug"><img src=images/teronbook.png width=250></a>
|
<a href="https://www.youtube.com/watch?v=OAoA3E-cyug"><img src=images/teronbook.png width=250></a>
|
||||||
|
|
||||||
This documentation is a reference and summarizes grammar syntax and the key semantics of ANTLR grammars. The source code for all examples in the book, not just this chapter, are free at the publisher's website. The following video is a general tour of ANTLR 4 and includes a description of how to use parse tree listeners to process Java files easily:
|
This documentation is a reference and summarizes grammar syntax and the key semantics of ANTLR grammars. The source code for all examples in the book, not just this chapter, are free at the publisher's website. The following video is a general tour of ANTLR 4 and includes a description of how to use parse tree listeners to process Java files easily:
|
||||||
|
|
||||||
<a href="https://vimeo.com/59285751"><img src=images/tertalk.png width=200></a>
|
<a href="https://vimeo.com/59285751"><img src=images/tertalk.png width=200></a>
|
||||||
|
@ -52,7 +52,7 @@ This documentation is a reference and summarizes grammar syntax and the key sema
|
||||||
* [Runtime Libraries and Code Generation Targets](targets.md)
|
* [Runtime Libraries and Code Generation Targets](targets.md)
|
||||||
|
|
||||||
* [Parsing binary streams](parsing-binary-files.md)
|
* [Parsing binary streams](parsing-binary-files.md)
|
||||||
|
|
||||||
* [Parser and lexer interpreters](interpreters.md)
|
* [Parser and lexer interpreters](interpreters.md)
|
||||||
|
|
||||||
* [Resources](resources.md)
|
* [Resources](resources.md)
|
||||||
|
@ -61,6 +61,8 @@ This documentation is a reference and summarizes grammar syntax and the key sema
|
||||||
|
|
||||||
* [Building ANTLR itself](building-antlr.md)
|
* [Building ANTLR itself](building-antlr.md)
|
||||||
|
|
||||||
|
* [Contributing to ANTLR](/CONTRIBUTING.md)
|
||||||
|
|
||||||
* [Cutting an ANTLR Release](releasing-antlr.md)
|
* [Cutting an ANTLR Release](releasing-antlr.md)
|
||||||
|
|
||||||
* [ANTLR project unit tests](antlr-project-testing.md)
|
* [ANTLR project unit tests](antlr-project-testing.md)
|
||||||
|
|
|
@ -15,7 +15,7 @@ The tests were conducted using Selenium. No issue was found, so you should find
|
||||||
|
|
||||||
## Is NodeJS supported?
|
## Is NodeJS supported?
|
||||||
|
|
||||||
The runtime has also been extensively tested against Node.js 0.10.33. No issue was found.
|
The runtime has also been extensively tested against Node.js 0.12.7. No issue was found.
|
||||||
|
|
||||||
## How to create a JavaScript lexer or parser?
|
## How to create a JavaScript lexer or parser?
|
||||||
|
|
||||||
|
@ -31,7 +31,9 @@ For a full list of antlr4 tool options, please visit the [tool documentation pag
|
||||||
|
|
||||||
Once you've generated the lexer and/or parser code, you need to download the runtime.
|
Once you've generated the lexer and/or parser code, you need to download the runtime.
|
||||||
|
|
||||||
The JavaScript runtime is available from the ANTLR web site [download section](http://www.antlr.org/download/index.html). The runtime is provided in the form of source code, so no additional installation is required.
|
The JavaScript runtime is [available from npm](https://www.npmjs.com/package/antlr4).
|
||||||
|
|
||||||
|
If you can't use npm, the JavaScript runtime is also available from the ANTLR web site [download section](http://www.antlr.org/download/index.html). The runtime is provided in the form of source code, so no additional installation is required.
|
||||||
|
|
||||||
We will not document here how to refer to the runtime from your project, since this would differ a lot depending on your project type and IDE.
|
We will not document here how to refer to the runtime from your project, since this would differ a lot depending on your project type and IDE.
|
||||||
|
|
||||||
|
@ -47,11 +49,28 @@ However, it would be a bit of a problem when it comes to get it into a browser.
|
||||||
<script src='lib/myscript.js'>
|
<script src='lib/myscript.js'>
|
||||||
```
|
```
|
||||||
|
|
||||||
In order to avoid having to do this, and also to have the exact same code for browsers and Node.js, we rely on a script which provides the equivalent of the Node.js 'require' function.
|
To avoid having doing this, the preferred approach is to bundle antlr4 with your parser code, using webpack.
|
||||||
|
|
||||||
This script is provided by Torben Haase, and is NOT part of ANTLR JavaScript runtime, although the runtime heavily relies on it. Please note that syntax for 'require' in NodeJS is different from the one implemented by RequireJS and similar frameworks.
|
You can get [information on webpack here](https://webpack.github.io).
|
||||||
|
|
||||||
So in short, assuming you have at the root of your web site, both the 'antlr4' directory and a 'lib' directory with 'require.js' inside it, all you need to put in your HTML header is the following:
|
The steps to create your parsing code are the following:
|
||||||
|
- generate your lexer, parser, listener and visitor using the antlr tool
|
||||||
|
- write your parse tree handling code by providig your custom listener or visitor, and associated code, using 'require' to load antlr.
|
||||||
|
- create an index.js file with the entry point to your parsing code (or several if required).
|
||||||
|
- test your parsing logic thoroughly using node.js
|
||||||
|
|
||||||
|
You are now ready to bundle your parsing code as follows:
|
||||||
|
- following webpack specs, create a webpack.config file
|
||||||
|
- in the webpack.config file, exclude node.js only modules using: node: { module: "empty", net: "empty", fs: "empty" }
|
||||||
|
- from the cmd line, nag-vigate to the directory containing webpack.config and type: webpack
|
||||||
|
|
||||||
|
This will produce a single js file containing all your parsing code. Easy to include in your web pages!
|
||||||
|
|
||||||
|
If you can't use webpack, you can use the lib/require.js script which implements the Node.js 'require' function in brwsers.
|
||||||
|
|
||||||
|
This script is provided by Torben Haase, and is NOT part of ANTLR JavaScript runtime.
|
||||||
|
|
||||||
|
Assuming you have, at the root of your web site, both the 'antlr4' directory and a 'lib' directory with 'require.js' inside it, all you need to put in your HTML header is the following:
|
||||||
|
|
||||||
```xml
|
```xml
|
||||||
<script src='lib/require.js'>
|
<script src='lib/require.js'>
|
||||||
|
@ -62,16 +81,6 @@ So in short, assuming you have at the root of your web site, both the 'antlr4' d
|
||||||
|
|
||||||
This will load the runtime asynchronously.
|
This will load the runtime asynchronously.
|
||||||
|
|
||||||
## How do I get the runtime in Node.js?
|
|
||||||
|
|
||||||
Right now, there is no npm package available, so you need to register a link instead. This can be done by running the following command from the antlr4 directory:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
$ npm link antlr4
|
|
||||||
```
|
|
||||||
|
|
||||||
This will install antlr4 using the package.json descriptor that comes with the script.
|
|
||||||
|
|
||||||
## How do I run the generated lexer and/or parser?
|
## How do I run the generated lexer and/or parser?
|
||||||
|
|
||||||
Let's suppose that your grammar is named, as above, "MyGrammar". Let's suppose this parser comprises a rule named "StartRule". The tool will have generated for you the following files:
|
Let's suppose that your grammar is named, as above, "MyGrammar". Let's suppose this parser comprises a rule named "StartRule". The tool will have generated for you the following files:
|
||||||
|
|
|
@ -33,21 +33,29 @@ Edit the repository looking for 4.5 or whatever and update it. Bump version in t
|
||||||
* runtime/Python3/src/antlr4/Recognizer.py
|
* runtime/Python3/src/antlr4/Recognizer.py
|
||||||
* runtime/CSharp/runtime/CSharp/Antlr4.Runtime/Properties/AssemblyInfo.cs
|
* runtime/CSharp/runtime/CSharp/Antlr4.Runtime/Properties/AssemblyInfo.cs
|
||||||
* runtime/CSharp/build/version.ps1
|
* runtime/CSharp/build/version.ps1
|
||||||
|
* runtime/CSharp/runtime/CSharp/Package.nuspec
|
||||||
* runtime/JavaScript/src/antlr4/package.json
|
* runtime/JavaScript/src/antlr4/package.json
|
||||||
* runtime/JavaScript/src/antlr4/Recognizer.js
|
* runtime/JavaScript/src/antlr4/Recognizer.js
|
||||||
* runtime/Cpp/VERSION
|
* runtime/Cpp/VERSION
|
||||||
* runtime/Cpp/runtime/src/RuntimeMetaData.cpp
|
* runtime/Cpp/runtime/src/RuntimeMetaData.cpp
|
||||||
* runtime/Cpp/cmake/ExternalAntlr4Cpp.cmake
|
* runtime/Cpp/cmake/ExternalAntlr4Cpp.cmake
|
||||||
|
* runtime/Cpp/demo/generate.cmd
|
||||||
|
* runtime/Go/antlr/recognizer.go
|
||||||
|
* runtime/Swift/Antlr4/org/antlr/v4/runtime/RuntimeMetaData.swift
|
||||||
|
* tool/src/org/antlr/v4/codegen/target/GoTarget.java
|
||||||
* tool/src/org/antlr/v4/codegen/target/CppTarget.java
|
* tool/src/org/antlr/v4/codegen/target/CppTarget.java
|
||||||
* tool/src/org/antlr/v4/codegen/target/CSharpTarget.java
|
* tool/src/org/antlr/v4/codegen/target/CSharpTarget.java
|
||||||
* tool/src/org/antlr/v4/codegen/target/JavaScriptTarget.java
|
* tool/src/org/antlr/v4/codegen/target/JavaScriptTarget.java
|
||||||
* tool/src/org/antlr/v4/codegen/target/Python2Target.java
|
* tool/src/org/antlr/v4/codegen/target/Python2Target.java
|
||||||
* tool/src/org/antlr/v4/codegen/target/Python3Target.java
|
* tool/src/org/antlr/v4/codegen/target/Python3Target.java
|
||||||
|
* tool/src/org/antlr/v4/codegen/target/SwiftTarget.java
|
||||||
|
* tool/src/org/antlr/v4/codegen/Target.java
|
||||||
|
* tool/resources/org/antlr/v4/tool/templates/codegen/Swift/Swift.stg
|
||||||
|
|
||||||
Here is a simple script to display any line from the critical files with, say, `4.5` in it:
|
Here is a simple script to display any line from the critical files with, say, `4.5` in it:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
find /tmp/antlr4 -type f -exec grep -l '4\.5' {} \;
|
find tool runtime -type f -exec grep -l '4\.6' {} \;
|
||||||
```
|
```
|
||||||
|
|
||||||
Commit to repository.
|
Commit to repository.
|
||||||
|
@ -301,7 +309,7 @@ rm Antlr4.Runtime/obj/net20/Release/Antlr4.Runtime.dll
|
||||||
# build
|
# build
|
||||||
xbuild /p:Configuration=Release Antlr4.Runtime/Antlr4.Runtime.mono.csproj
|
xbuild /p:Configuration=Release Antlr4.Runtime/Antlr4.Runtime.mono.csproj
|
||||||
# zip it up to get a version number on zip filename
|
# zip it up to get a version number on zip filename
|
||||||
zip --junk-paths /tmp/antlr-csharp-runtime-4.6.zip Antlr4.Runtime/bin/net35/Release/Antlr4.Runtime.dll
|
zip --junk-paths /tmp/antlr-csharp-runtime-4.6.zip Antlr4.Runtime/obj/net20/Release/Antlr4.Runtime.Standard.dll
|
||||||
cp /tmp/antlr-csharp-runtime-4.6.zip ~/antlr/sites/website-antlr4/download
|
cp /tmp/antlr-csharp-runtime-4.6.zip ~/antlr/sites/website-antlr4/download
|
||||||
```
|
```
|
||||||
|
|
||||||
|
@ -358,7 +366,7 @@ python setup.py register -r pypi
|
||||||
python setup.py sdist bdist_wininst upload -r pypi
|
python setup.py sdist bdist_wininst upload -r pypi
|
||||||
```
|
```
|
||||||
|
|
||||||
Add links to the artifacts from download.html
|
There are links to the artifacts in [download.html](http://www.antlr.org/download.html) already.
|
||||||
|
|
||||||
### C++
|
### C++
|
||||||
|
|
||||||
|
@ -378,6 +386,7 @@ On a Mac (with XCode 7+ installed):
|
||||||
```bash
|
```bash
|
||||||
cd runtime/Cpp
|
cd runtime/Cpp
|
||||||
./deploy-macos.sh
|
./deploy-macos.sh
|
||||||
|
cp antlr4-cpp-runtime-macos.zip ~/antlr/sites/website-antlr4/download/antlr4-cpp-runtime-4.6-macos.zip
|
||||||
```
|
```
|
||||||
|
|
||||||
On any Mac or Linux machine:
|
On any Mac or Linux machine:
|
||||||
|
@ -385,6 +394,7 @@ On any Mac or Linux machine:
|
||||||
```bash
|
```bash
|
||||||
cd runtime/Cpp
|
cd runtime/Cpp
|
||||||
./deploy-source.sh
|
./deploy-source.sh
|
||||||
|
cp antlr4-cpp-runtime-source.zip ~/antlr/sites/website-antlr4/download/antlr4-cpp-runtime-4.6-source.zip
|
||||||
```
|
```
|
||||||
|
|
||||||
On a Windows machine the build scripts checks if VS 2013 and/or VS 2015 are installed and builds binaries for each, if found. This script requires 7z to be installed (http://7-zip.org).
|
On a Windows machine the build scripts checks if VS 2013 and/or VS 2015 are installed and builds binaries for each, if found. This script requires 7z to be installed (http://7-zip.org).
|
||||||
|
@ -392,15 +402,17 @@ On a Windows machine the build scripts checks if VS 2013 and/or VS 2015 are inst
|
||||||
```bash
|
```bash
|
||||||
cd runtime/Cpp
|
cd runtime/Cpp
|
||||||
deploy-windows.cmd
|
deploy-windows.cmd
|
||||||
|
cp antlr4-cpp-runtime-vs2015.zip ~/antlr/sites/website-antlr4/download/antlr4-cpp-runtime-4.6-vs2015.zip
|
||||||
```
|
```
|
||||||
|
|
||||||
Move target to website (**_rename to a specific ANTLR version first if needed_**):
|
Move target to website (**_rename to a specific ANTLR version first if needed_**):
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
pushd ~/antlr/sites/website-antlr4/download
|
pushd ~/antlr/sites/website-antlr4/download
|
||||||
git add antlr4cpp-runtime-macos.zip
|
# vi index.html
|
||||||
git add antlr4cpp-runtime-windows.zip
|
git add antlr4cpp-runtime-4.6-macos.zip
|
||||||
git add antlr4cpp-runtime-source.zip
|
git add antlr4cpp-runtime-4.6-windows.zip
|
||||||
|
git add antlr4cpp-runtime-4.6-source.zip
|
||||||
git commit -a -m 'update C++ runtime'
|
git commit -a -m 'update C++ runtime'
|
||||||
git push origin gh-pages
|
git push origin gh-pages
|
||||||
popd
|
popd
|
||||||
|
@ -408,7 +420,7 @@ popd
|
||||||
|
|
||||||
## Update javadoc for runtime and tool
|
## Update javadoc for runtime and tool
|
||||||
|
|
||||||
First gen javadoc:
|
First, gen javadoc:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
$ cd antlr4
|
$ cd antlr4
|
||||||
|
|
2
pom.xml
2
pom.xml
|
@ -13,7 +13,7 @@
|
||||||
</parent>
|
</parent>
|
||||||
<groupId>org.antlr</groupId>
|
<groupId>org.antlr</groupId>
|
||||||
<artifactId>antlr4-master</artifactId>
|
<artifactId>antlr4-master</artifactId>
|
||||||
<version>4.6</version>
|
<version>4.6.1-SNAPSHOT</version>
|
||||||
<packaging>pom</packaging>
|
<packaging>pom</packaging>
|
||||||
|
|
||||||
<name>ANTLR 4</name>
|
<name>ANTLR 4</name>
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.antlr</groupId>
|
<groupId>org.antlr</groupId>
|
||||||
<artifactId>antlr4-master</artifactId>
|
<artifactId>antlr4-master</artifactId>
|
||||||
<version>4.6</version>
|
<version>4.6.1-SNAPSHOT</version>
|
||||||
<relativePath>../../pom.xml</relativePath>
|
<relativePath>../../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<artifactId>antlr4-runtime-test-annotations</artifactId>
|
<artifactId>antlr4-runtime-test-annotations</artifactId>
|
||||||
|
|
|
@ -10,7 +10,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.antlr</groupId>
|
<groupId>org.antlr</groupId>
|
||||||
<artifactId>antlr4-master</artifactId>
|
<artifactId>antlr4-master</artifactId>
|
||||||
<version>4.6</version>
|
<version>4.6.1-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<artifactId>antlr4-runtime-testsuite</artifactId>
|
<artifactId>antlr4-runtime-testsuite</artifactId>
|
||||||
<name>ANTLR 4 Runtime Tests (2nd generation)</name>
|
<name>ANTLR 4 Runtime Tests (2nd generation)</name>
|
||||||
|
@ -95,6 +95,8 @@
|
||||||
<artifactId>maven-surefire-plugin</artifactId>
|
<artifactId>maven-surefire-plugin</artifactId>
|
||||||
<version>2.19.1</version>
|
<version>2.19.1</version>
|
||||||
<configuration>
|
<configuration>
|
||||||
|
<!-- SUREFIRE-951: file.encoding cannot be set via systemPropertyVariables -->
|
||||||
|
<argLine>-Dfile.encoding=UTF-8</argLine>
|
||||||
<includes>
|
<includes>
|
||||||
<include>**/csharp/Test*.java</include>
|
<include>**/csharp/Test*.java</include>
|
||||||
<include>**/java/Test*.java</include>
|
<include>**/java/Test*.java</include>
|
||||||
|
@ -118,6 +120,24 @@
|
||||||
</execution>
|
</execution>
|
||||||
</executions>
|
</executions>
|
||||||
</plugin>
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.antlr</groupId>
|
||||||
|
<artifactId>antlr4-maven-plugin</artifactId>
|
||||||
|
<version>${project.version}</version>
|
||||||
|
<executions>
|
||||||
|
<execution>
|
||||||
|
<goals>
|
||||||
|
<goal>antlr4</goal>
|
||||||
|
</goals>
|
||||||
|
<configuration>
|
||||||
|
<sourceDirectory>${basedir}/test</sourceDirectory>
|
||||||
|
<outputDirectory>${project.build.directory}/generated-test-sources/antlr4</outputDirectory>
|
||||||
|
<visitor>true</visitor>
|
||||||
|
<generateTestSources>true</generateTestSources>
|
||||||
|
</configuration>
|
||||||
|
</execution>
|
||||||
|
</executions>
|
||||||
|
</plugin>
|
||||||
</plugins>
|
</plugins>
|
||||||
</build>
|
</build>
|
||||||
|
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.antlr</groupId>
|
<groupId>org.antlr</groupId>
|
||||||
<artifactId>antlr4-master</artifactId>
|
<artifactId>antlr4-master</artifactId>
|
||||||
<version>4.6</version>
|
<version>4.6.1-SNAPSHOT</version>
|
||||||
<relativePath>../../pom.xml</relativePath>
|
<relativePath>../../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<artifactId>antlr4-runtime-test-annotation-processors</artifactId>
|
<artifactId>antlr4-runtime-test-annotation-processors</artifactId>
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
writeln(s) ::= <<Console.WriteLine(<s>);>>
|
writeln(s) ::= <<Output.WriteLine(<s>);>>
|
||||||
write(s) ::= <<Console.Write(<s>);>>
|
write(s) ::= <<Output.Write(<s>);>>
|
||||||
writeList(s) ::= <<Console.WriteLine(<s; separator="+">);>>
|
writeList(s) ::= <<Output.WriteLine(<s; separator="+">);>>
|
||||||
|
|
||||||
False() ::= "false"
|
False() ::= "false"
|
||||||
|
|
||||||
|
@ -176,8 +176,14 @@ public class PositionAdjustingLexerATNSimulator : LexerATNSimulator {
|
||||||
BasicListener(X) ::= <<
|
BasicListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
public class LeafListener : TBaseListener {
|
public class LeafListener : TBaseListener {
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public LeafListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public override void VisitTerminal(ITerminalNode node) {
|
public override void VisitTerminal(ITerminalNode node) {
|
||||||
Console.WriteLine(node.Symbol.Text);
|
Output.WriteLine(node.Symbol.Text);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -185,7 +191,7 @@ public class LeafListener : TBaseListener {
|
||||||
|
|
||||||
WalkListener(s) ::= <<
|
WalkListener(s) ::= <<
|
||||||
ParseTreeWalker walker = new ParseTreeWalker();
|
ParseTreeWalker walker = new ParseTreeWalker();
|
||||||
walker.Walk(new LeafListener(), <s>);
|
walker.Walk(new LeafListener(Output), <s>);
|
||||||
>>
|
>>
|
||||||
|
|
||||||
TreeNodeWithAltNumField(X) ::= <<
|
TreeNodeWithAltNumField(X) ::= <<
|
||||||
|
@ -204,6 +210,12 @@ public class MyRuleNode : ParserRuleContext {
|
||||||
TokenGetterListener(X) ::= <<
|
TokenGetterListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
public class LeafListener : TBaseListener {
|
public class LeafListener : TBaseListener {
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public LeafListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public override void ExitA(TParser.AContext ctx) {
|
public override void ExitA(TParser.AContext ctx) {
|
||||||
if (ctx.ChildCount==2)
|
if (ctx.ChildCount==2)
|
||||||
{
|
{
|
||||||
|
@ -214,11 +226,11 @@ public class LeafListener : TBaseListener {
|
||||||
}
|
}
|
||||||
sb.Length = sb.Length - 2;
|
sb.Length = sb.Length - 2;
|
||||||
sb.Append ("]");
|
sb.Append ("]");
|
||||||
Console.Write ("{0} {1} {2}", ctx.INT (0).Symbol.Text,
|
Output.Write ("{0} {1} {2}", ctx.INT (0).Symbol.Text,
|
||||||
ctx.INT (1).Symbol.Text, sb.ToString());
|
ctx.INT (1).Symbol.Text, sb.ToString());
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
Console.WriteLine(ctx.ID().Symbol);
|
Output.WriteLine(ctx.ID().Symbol);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -227,12 +239,18 @@ public class LeafListener : TBaseListener {
|
||||||
RuleGetterListener(X) ::= <<
|
RuleGetterListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
public class LeafListener : TBaseListener {
|
public class LeafListener : TBaseListener {
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public LeafListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public override void ExitA(TParser.AContext ctx) {
|
public override void ExitA(TParser.AContext ctx) {
|
||||||
if (ctx.ChildCount==2) {
|
if (ctx.ChildCount==2) {
|
||||||
Console.Write("{0} {1} {2}",ctx.b(0).Start.Text,
|
Output.Write("{0} {1} {2}",ctx.b(0).Start.Text,
|
||||||
ctx.b(1).Start.Text,ctx.b()[0].Start.Text);
|
ctx.b(1).Start.Text,ctx.b()[0].Start.Text);
|
||||||
} else
|
} else
|
||||||
Console.WriteLine(ctx.b(0).Start.Text);
|
Output.WriteLine(ctx.b(0).Start.Text);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -242,12 +260,18 @@ public class LeafListener : TBaseListener {
|
||||||
LRListener(X) ::= <<
|
LRListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
public class LeafListener : TBaseListener {
|
public class LeafListener : TBaseListener {
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public LeafListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public override void ExitE(TParser.EContext ctx) {
|
public override void ExitE(TParser.EContext ctx) {
|
||||||
if (ctx.ChildCount==3) {
|
if (ctx.ChildCount==3) {
|
||||||
Console.Write("{0} {1} {2}\n",ctx.e(0).Start.Text,
|
Output.Write("{0} {1} {2}\n",ctx.e(0).Start.Text,
|
||||||
ctx.e(1).Start.Text, ctx.e()[0].Start.Text);
|
ctx.e(1).Start.Text, ctx.e()[0].Start.Text);
|
||||||
} else
|
} else
|
||||||
Console.WriteLine(ctx.INT().Symbol.Text);
|
Output.WriteLine(ctx.INT().Symbol.Text);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -256,24 +280,22 @@ public class LeafListener : TBaseListener {
|
||||||
LRWithLabelsListener(X) ::= <<
|
LRWithLabelsListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
public class LeafListener : TBaseListener {
|
public class LeafListener : TBaseListener {
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public LeafListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public override void ExitCall(TParser.CallContext ctx) {
|
public override void ExitCall(TParser.CallContext ctx) {
|
||||||
Console.Write("{0} {1}",ctx.e().Start.Text,ctx.eList());
|
Output.Write("{0} {1}",ctx.e().Start.Text,ctx.eList());
|
||||||
}
|
}
|
||||||
public override void ExitInt(TParser.IntContext ctx) {
|
public override void ExitInt(TParser.IntContext ctx) {
|
||||||
Console.WriteLine(ctx.INT().Symbol.Text);
|
Output.WriteLine(ctx.INT().Symbol.Text);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
void foo() {
|
void foo() {
|
||||||
SContext s = null;
|
SContext s = null;
|
||||||
|
@ -282,12 +304,12 @@ void foo() {
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
Declare_foo() ::= <<public void foo() {Console.WriteLine("foo");}>>
|
Declare_foo() ::= <<public void foo() {Output.WriteLine("foo");}>>
|
||||||
|
|
||||||
Invoke_foo() ::= "this.foo();"
|
Invoke_foo() ::= "this.foo();"
|
||||||
|
|
||||||
Declare_pred() ::= <<bool pred(bool v) {
|
Declare_pred() ::= <<bool pred(bool v) {
|
||||||
Console.WriteLine("eval="+v.ToString().ToLower());
|
Output.WriteLine("eval="+v.ToString().ToLower());
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
|
@ -243,14 +243,6 @@ public:
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
void foo() {
|
void foo() {
|
||||||
SContext *s;
|
SContext *s;
|
||||||
|
|
|
@ -298,14 +298,6 @@ func (*LeafListener) ExitInt(ctx *IntContext) {
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
func foo() {
|
func foo() {
|
||||||
// TODO
|
// TODO
|
||||||
|
@ -333,5 +325,5 @@ func pred(v bool) bool {
|
||||||
|
|
||||||
Invoke_pred(v) ::= <<pred(<v>)>>
|
Invoke_pred(v) ::= <<pred(<v>)>>
|
||||||
ContextRuleFunction(ctx, rule) ::= "<ctx>.<rule>"
|
ContextRuleFunction(ctx, rule) ::= "<ctx>.<rule>"
|
||||||
StringType() ::= "String"
|
StringType() ::= "string"
|
||||||
ContextMember(ctx, subctx, member) ::= "<ctx>.<subctx>.<member; format={cap}>"
|
ContextMember(ctx, subctx, member) ::= "<ctx>.<subctx>.<member; format={cap}>"
|
||||||
|
|
|
@ -262,14 +262,6 @@ public static class LeafListener extends TBaseListener {
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
void foo() {
|
void foo() {
|
||||||
SContext s = null;
|
SContext s = null;
|
||||||
|
|
|
@ -76,8 +76,6 @@ var <X>Listener = require('./<X>Listener').<X>Listener;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= <<var <X>Visitor = require('./<X>Visitor').<X>Visitor;>>
|
|
||||||
|
|
||||||
GetExpectedTokenNames() ::= "this.getExpectedTokens().toString(this.literalNames)"
|
GetExpectedTokenNames() ::= "this.getExpectedTokens().toString(this.literalNames)"
|
||||||
|
|
||||||
RuleInvocationStack() ::= "antlr4.Utils.arrayToString(this.getRuleInvocationStack())"
|
RuleInvocationStack() ::= "antlr4.Utils.arrayToString(this.getRuleInvocationStack())"
|
||||||
|
@ -182,24 +180,6 @@ var walker = new antlr4.tree.ParseTreeWalker();
|
||||||
walker.walk(new this.LeafListener(), <s>);
|
walker.walk(new this.LeafListener(), <s>);
|
||||||
>>
|
>>
|
||||||
|
|
||||||
BasicVisitor(X) ::= <<
|
|
||||||
this.LeafVisitor = function() {
|
|
||||||
this.visitTerminal = function(node) {
|
|
||||||
return node.symbol.text;
|
|
||||||
};
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
this.LeafVisitor.prototype = Object.create(<X>Visitor.prototype);
|
|
||||||
this.LeafVisitor.prototype.constructor = this.LeafVisitor;
|
|
||||||
|
|
||||||
>>
|
|
||||||
|
|
||||||
WalkVisitor(s) ::= <<
|
|
||||||
var visitor = new this.LeafVisitor();
|
|
||||||
console.log(<s>.accept(visitor));
|
|
||||||
>>
|
|
||||||
|
|
||||||
|
|
||||||
TreeNodeWithAltNumField(X) ::= <<
|
TreeNodeWithAltNumField(X) ::= <<
|
||||||
@parser::header {
|
@parser::header {
|
||||||
MyRuleNode = function(parent, invokingState) {
|
MyRuleNode = function(parent, invokingState) {
|
||||||
|
@ -236,24 +216,6 @@ this.LeafListener.prototype.constructor = this.LeafListener;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
TokenGetterVisitor(X) ::= <<
|
|
||||||
this.LeafVisitor = function() {
|
|
||||||
this.visitA = function(ctx) {
|
|
||||||
var str;
|
|
||||||
if(ctx.getChildCount()===2) {
|
|
||||||
str = ctx.INT(0).symbol.text + ' ' + ctx.INT(1).symbol.text + ' ' + antlr4.Utils.arrayToString(ctx.INT());
|
|
||||||
} else {
|
|
||||||
str = ctx.ID().symbol.toString();
|
|
||||||
}
|
|
||||||
return this.visitChildren(ctx) + str;
|
|
||||||
};
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
this.LeafVisitor.prototype = Object.create(<X>Visitor.prototype);
|
|
||||||
this.LeafVisitor.prototype.constructor = this.LeafVisitor;
|
|
||||||
|
|
||||||
>>
|
|
||||||
|
|
||||||
RuleGetterListener(X) ::= <<
|
RuleGetterListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
this.LeafListener = function() {
|
this.LeafListener = function() {
|
||||||
|
@ -273,25 +235,6 @@ this.LeafListener.prototype.constructor = this.LeafListener;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
RuleGetterVisitor(X) ::= <<
|
|
||||||
this.LeafVisitor = function() {
|
|
||||||
this.visitA = function(ctx) {
|
|
||||||
var str;
|
|
||||||
if(ctx.getChildCount()===2) {
|
|
||||||
str = ctx.b(0).start.text + ' ' + ctx.b(1).start.text + ' ' + ctx.b()[0].start.text;
|
|
||||||
} else {
|
|
||||||
str = ctx.b(0).start.text;
|
|
||||||
}
|
|
||||||
return this.visitChildren(ctx) + str;
|
|
||||||
};
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
this.LeafVisitor.prototype = Object.create(<X>Visitor.prototype);
|
|
||||||
this.LeafVisitor.prototype.constructor = this.LeafVisitor;
|
|
||||||
|
|
||||||
>>
|
|
||||||
|
|
||||||
|
|
||||||
LRListener(X) ::= <<
|
LRListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
this.LeafListener = function() {
|
this.LeafListener = function() {
|
||||||
|
@ -311,24 +254,6 @@ this.LeafListener.prototype.constructor = this.LeafListener;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
LRVisitor(X) ::= <<
|
|
||||||
this.LeafVisitor = function() {
|
|
||||||
this.visitE = function(ctx) {
|
|
||||||
var str;
|
|
||||||
if(ctx.getChildCount()===3) {
|
|
||||||
str = ctx.e(0).start.text + ' ' + ctx.e(1).start.text + ' ' + ctx.e()[0].start.text;
|
|
||||||
} else {
|
|
||||||
str = ctx.INT().symbol.text;
|
|
||||||
}
|
|
||||||
return this.visitChildren(ctx) + str;
|
|
||||||
};
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
this.LeafVisitor.prototype = Object.create(<X>Visitor.prototype);
|
|
||||||
this.LeafVisitor.prototype.constructor = this.LeafVisitor;
|
|
||||||
|
|
||||||
>>
|
|
||||||
|
|
||||||
LRWithLabelsListener(X) ::= <<
|
LRWithLabelsListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
this.LeafListener = function() {
|
this.LeafListener = function() {
|
||||||
|
@ -347,23 +272,6 @@ this.LeafListener.prototype.constructor = this.LeafListener;
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
LRWithLabelsVisitor(X) ::= <<
|
|
||||||
this.LeafVisitor = function() {
|
|
||||||
this.visitCall = function(ctx) {
|
|
||||||
var str = ctx.e().start.text + ' ' + ctx.eList();
|
|
||||||
return this.visitChildren(ctx) + str;
|
|
||||||
};
|
|
||||||
this.visitInt = function(ctx) {
|
|
||||||
var str = ctx.INT().symbol.text;
|
|
||||||
return this.visitChildren(ctx) + str;
|
|
||||||
};
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
this.LeafVisitor.prototype = Object.create(<X>Visitor.prototype);
|
|
||||||
this.LeafVisitor.prototype.constructor = this.LeafVisitor;
|
|
||||||
|
|
||||||
>>
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
function foo() {
|
function foo() {
|
||||||
var s = new SContext();
|
var s = new SContext();
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
writeln(s) ::= <<print(<s>)>>
|
writeln(s) ::= <<print(<s>, file=self._output)>>
|
||||||
write(s) ::= <<print(<s>,end='')>>
|
write(s) ::= <<print(<s>,end='', file=self._output)>>
|
||||||
writeList(s) ::= <<print(<s: {v | str(<v>)}; separator="+">)>>
|
writeList(s) ::= <<print(<s: {v | str(<v>)}; separator="+">, file=self._output)>>
|
||||||
|
|
||||||
False() ::= "False"
|
False() ::= "False"
|
||||||
|
|
||||||
|
@ -152,14 +152,16 @@ else:
|
||||||
from <X>Listener import <X>Listener
|
from <X>Listener import <X>Listener
|
||||||
|
|
||||||
class LeafListener(TListener):
|
class LeafListener(TListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def visitTerminal(self, node):
|
def visitTerminal(self, node):
|
||||||
print(node.symbol.text)
|
print(node.symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
WalkListener(s) ::= <<
|
WalkListener(s) ::= <<
|
||||||
walker = ParseTreeWalker()
|
walker = ParseTreeWalker()
|
||||||
walker.walk(TParser.LeafListener(), <s>)
|
walker.walk(TParser.LeafListener(self._output), <s>)
|
||||||
>>
|
>>
|
||||||
|
|
||||||
TreeNodeWithAltNumField(X) ::= <<
|
TreeNodeWithAltNumField(X) ::= <<
|
||||||
|
@ -183,11 +185,13 @@ else:
|
||||||
from <X>Listener import <X>Listener
|
from <X>Listener import <X>Listener
|
||||||
|
|
||||||
class LeafListener(TListener):
|
class LeafListener(TListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitA(self, ctx):
|
def exitA(self, ctx):
|
||||||
if ctx.getChildCount()==2:
|
if ctx.getChildCount()==2:
|
||||||
print(ctx.INT(0).symbol.text + ' ' + ctx.INT(1).symbol.text + ' ' + str_list(ctx.INT()))
|
print(ctx.INT(0).symbol.text + ' ' + ctx.INT(1).symbol.text + ' ' + str_list(ctx.INT()), file=self._output)
|
||||||
else:
|
else:
|
||||||
print(str(ctx.ID().symbol))
|
print(str(ctx.ID().symbol), file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
|
@ -199,11 +203,13 @@ else:
|
||||||
from <X>Listener import <X>Listener
|
from <X>Listener import <X>Listener
|
||||||
|
|
||||||
class LeafListener(TListener):
|
class LeafListener(TListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitA(self, ctx):
|
def exitA(self, ctx):
|
||||||
if ctx.getChildCount()==2:
|
if ctx.getChildCount()==2:
|
||||||
print(ctx.b(0).start.text + ' ' + ctx.b(1).start.text + ' ' + ctx.b()[0].start.text)
|
print(ctx.b(0).start.text + ' ' + ctx.b(1).start.text + ' ' + ctx.b()[0].start.text, file=self._output)
|
||||||
else:
|
else:
|
||||||
print(ctx.b(0).start.text)
|
print(ctx.b(0).start.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
|
@ -216,11 +222,13 @@ else:
|
||||||
from <X>Listener import <X>Listener
|
from <X>Listener import <X>Listener
|
||||||
|
|
||||||
class LeafListener(TListener):
|
class LeafListener(TListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitE(self, ctx):
|
def exitE(self, ctx):
|
||||||
if ctx.getChildCount()==3:
|
if ctx.getChildCount()==3:
|
||||||
print(ctx.e(0).start.text + ' ' + ctx.e(1).start.text + ' ' + ctx.e()[0].start.text)
|
print(ctx.e(0).start.text + ' ' + ctx.e(1).start.text + ' ' + ctx.e()[0].start.text, file=self._output)
|
||||||
else:
|
else:
|
||||||
print(ctx.INT().symbol.text)
|
print(ctx.INT().symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
|
@ -232,21 +240,15 @@ else:
|
||||||
from <X>Listener import <X>Listener
|
from <X>Listener import <X>Listener
|
||||||
|
|
||||||
class LeafListener(TListener):
|
class LeafListener(TListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitCall(self, ctx):
|
def exitCall(self, ctx):
|
||||||
print(ctx.e().start.text + ' ' + str(ctx.eList()))
|
print(ctx.e().start.text + ' ' + str(ctx.eList()), file=self._output)
|
||||||
def exitInt(self, ctx):
|
def exitInt(self, ctx):
|
||||||
print(ctx.INT().symbol.text)
|
print(ctx.INT().symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
def foo():
|
def foo():
|
||||||
s = SContext()
|
s = SContext()
|
||||||
|
@ -255,13 +257,13 @@ def foo():
|
||||||
>>
|
>>
|
||||||
|
|
||||||
Declare_foo() ::= <<def foo(self):
|
Declare_foo() ::= <<def foo(self):
|
||||||
print('foo')
|
print('foo', file=self._output)
|
||||||
>>
|
>>
|
||||||
|
|
||||||
Invoke_foo() ::= "self.foo()"
|
Invoke_foo() ::= "self.foo()"
|
||||||
|
|
||||||
Declare_pred() ::= <<def pred(self, v):
|
Declare_pred() ::= <<def pred(self, v):
|
||||||
print('eval=' + str(v).lower())
|
print('eval=' + str(v).lower(), file=self._output)
|
||||||
return v
|
return v
|
||||||
|
|
||||||
>>
|
>>
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
writeln(s) ::= <<print(<s>)>>
|
writeln(s) ::= <<print(<s>, file=self._output)>>
|
||||||
write(s) ::= <<print(<s>,end='')>>
|
write(s) ::= <<print(<s>,end='',file=self._output)>>
|
||||||
writeList(s) ::= <<print(<s: {v | str(<v>)}; separator="+">)>>
|
writeList(s) ::= <<print(<s: {v | str(<v>)}; separator="+">, file=self._output)>>
|
||||||
|
|
||||||
False() ::= "False"
|
False() ::= "False"
|
||||||
|
|
||||||
|
@ -152,8 +152,10 @@ def isIdentifierChar(c):
|
||||||
BasicListener(X) ::= <<
|
BasicListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
class LeafListener(MockListener):
|
class LeafListener(MockListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def visitTerminal(self, node):
|
def visitTerminal(self, node):
|
||||||
print(node.symbol.text)
|
print(node.symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
|
@ -164,7 +166,7 @@ else:
|
||||||
from TListener import TListener
|
from TListener import TListener
|
||||||
TParser.LeafListener.__bases__ = (TListener,)
|
TParser.LeafListener.__bases__ = (TListener,)
|
||||||
walker = ParseTreeWalker()
|
walker = ParseTreeWalker()
|
||||||
walker.walk(TParser.LeafListener(), <s>)
|
walker.walk(TParser.LeafListener(self._output), <s>)
|
||||||
>>
|
>>
|
||||||
|
|
||||||
TreeNodeWithAltNumField(X) ::= <<
|
TreeNodeWithAltNumField(X) ::= <<
|
||||||
|
@ -183,22 +185,26 @@ class MyRuleNode(ParserRuleContext):
|
||||||
TokenGetterListener(X) ::= <<
|
TokenGetterListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
class LeafListener(MockListener):
|
class LeafListener(MockListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitA(self, ctx):
|
def exitA(self, ctx):
|
||||||
if ctx.getChildCount()==2:
|
if ctx.getChildCount()==2:
|
||||||
print(ctx.INT(0).symbol.text + ' ' + ctx.INT(1).symbol.text + ' ' + str_list(ctx.INT()))
|
print(ctx.INT(0).symbol.text + ' ' + ctx.INT(1).symbol.text + ' ' + str_list(ctx.INT()), file=self._output)
|
||||||
else:
|
else:
|
||||||
print(str(ctx.ID().symbol))
|
print(str(ctx.ID().symbol), file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
RuleGetterListener(X) ::= <<
|
RuleGetterListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
class LeafListener(MockListener):
|
class LeafListener(MockListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitA(self, ctx):
|
def exitA(self, ctx):
|
||||||
if ctx.getChildCount()==2:
|
if ctx.getChildCount()==2:
|
||||||
print(ctx.b(0).start.text + ' ' + ctx.b(1).start.text + ' ' + ctx.b()[0].start.text)
|
print(ctx.b(0).start.text + ' ' + ctx.b(1).start.text + ' ' + ctx.b()[0].start.text, file=self._output)
|
||||||
else:
|
else:
|
||||||
print(ctx.b(0).start.text)
|
print(ctx.b(0).start.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
|
@ -206,32 +212,28 @@ class LeafListener(MockListener):
|
||||||
LRListener(X) ::= <<
|
LRListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
class LeafListener(MockListener):
|
class LeafListener(MockListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitE(self, ctx):
|
def exitE(self, ctx):
|
||||||
if ctx.getChildCount()==3:
|
if ctx.getChildCount()==3:
|
||||||
print(ctx.e(0).start.text + ' ' + ctx.e(1).start.text + ' ' + ctx.e()[0].start.text)
|
print(ctx.e(0).start.text + ' ' + ctx.e(1).start.text + ' ' + ctx.e()[0].start.text, file=self._output)
|
||||||
else:
|
else:
|
||||||
print(ctx.INT().symbol.text)
|
print(ctx.INT().symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
LRWithLabelsListener(X) ::= <<
|
LRWithLabelsListener(X) ::= <<
|
||||||
@parser::members {
|
@parser::members {
|
||||||
class LeafListener(MockListener):
|
class LeafListener(MockListener):
|
||||||
|
def __init__(self, output):
|
||||||
|
self._output = output
|
||||||
def exitCall(self, ctx):
|
def exitCall(self, ctx):
|
||||||
print(ctx.e().start.text + ' ' + str(ctx.eList()))
|
print(ctx.e().start.text + ' ' + str(ctx.eList()), file=self._output)
|
||||||
def exitInt(self, ctx):
|
def exitInt(self, ctx):
|
||||||
print(ctx.INT().symbol.text)
|
print(ctx.INT().symbol.text, file=self._output)
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
def foo():
|
def foo():
|
||||||
s = SContext()
|
s = SContext()
|
||||||
|
@ -240,13 +242,13 @@ def foo():
|
||||||
>>
|
>>
|
||||||
|
|
||||||
Declare_foo() ::= <<def foo(self):
|
Declare_foo() ::= <<def foo(self):
|
||||||
print('foo')
|
print('foo', file=self._output)
|
||||||
>>
|
>>
|
||||||
|
|
||||||
Invoke_foo() ::= "self.foo()"
|
Invoke_foo() ::= "self.foo()"
|
||||||
|
|
||||||
Declare_pred() ::= <<def pred(self, v):
|
Declare_pred() ::= <<def pred(self, v):
|
||||||
print('eval=' + str(v).lower())
|
print('eval=' + str(v).lower(), file=self._output)
|
||||||
return v
|
return v
|
||||||
|
|
||||||
>>
|
>>
|
||||||
|
|
|
@ -271,14 +271,6 @@ open class LeafListener: TBaseListener {
|
||||||
}
|
}
|
||||||
>>
|
>>
|
||||||
|
|
||||||
ImportVisitor(X) ::= ""
|
|
||||||
BasicVisitor(X) ::= ""
|
|
||||||
WalkVisitor(s) ::= ""
|
|
||||||
LRWithLabelsVisitor(X) ::= ""
|
|
||||||
RuleGetterVisitor(X) ::= ""
|
|
||||||
LRVisitor(x) ::= ""
|
|
||||||
TokenGetterVisitor(x) ::= ""
|
|
||||||
|
|
||||||
DeclareContextListGettersFunction() ::= <<
|
DeclareContextListGettersFunction() ::= <<
|
||||||
func foo() {
|
func foo() {
|
||||||
//let s: SContext? = nil
|
//let s: SContext? = nil
|
||||||
|
|
|
@ -224,7 +224,7 @@ public abstract class BaseRuntimeTest {
|
||||||
String... extraOptions)
|
String... extraOptions)
|
||||||
{
|
{
|
||||||
mkdir(workdir);
|
mkdir(workdir);
|
||||||
BaseJavaTest.writeFile(workdir, grammarFileName, grammarStr);
|
writeFile(workdir, grammarFileName, grammarStr);
|
||||||
return antlrOnString(workdir, targetName, grammarFileName, defaultListener, extraOptions);
|
return antlrOnString(workdir, targetName, grammarFileName, defaultListener, extraOptions);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,42 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime;
|
||||||
|
|
||||||
|
import java.io.BufferedReader;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.InputStreamReader;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
|
public final class StreamVacuum implements Runnable {
|
||||||
|
private StringBuilder buf = new StringBuilder();
|
||||||
|
private BufferedReader in;
|
||||||
|
private Thread sucker;
|
||||||
|
public StreamVacuum(InputStream in) {
|
||||||
|
this.in = new BufferedReader( new InputStreamReader(in, StandardCharsets.UTF_8) );
|
||||||
|
}
|
||||||
|
public void start() {
|
||||||
|
sucker = new Thread(this);
|
||||||
|
sucker.start();
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
try {
|
||||||
|
TestOutputReading.append(in, buf);
|
||||||
|
}
|
||||||
|
catch (IOException ioe) {
|
||||||
|
System.err.println("can't read output from process");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/** wait for the thread to finish */
|
||||||
|
public void join() throws InterruptedException {
|
||||||
|
sucker.join();
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return buf.toString();
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,64 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime;
|
||||||
|
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.nio.file.Files;
|
||||||
|
import java.nio.file.NoSuchFileException;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
import java.io.BufferedReader;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public abstract class TestOutputReading {
|
||||||
|
public static void append(BufferedReader in, StringBuilder buf) throws IOException {
|
||||||
|
String line = in.readLine();
|
||||||
|
while (line!=null) {
|
||||||
|
buf.append(line);
|
||||||
|
// NOTE: This appends a newline at EOF
|
||||||
|
// regardless of whether or not the
|
||||||
|
// input actually ended with a
|
||||||
|
// newline.
|
||||||
|
//
|
||||||
|
// We should revisit this and read a
|
||||||
|
// block at a time rather than a line
|
||||||
|
// at a time, and change all tests
|
||||||
|
// which rely on this behavior to
|
||||||
|
// remove the trailing newline at EOF.
|
||||||
|
//
|
||||||
|
// When we fix this, we can remove the
|
||||||
|
// TestOutputReading class entirely.
|
||||||
|
buf.append('\n');
|
||||||
|
line = in.readLine();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Read in the UTF-8 bytes at {@code path}, convert all
|
||||||
|
* platform-specific line terminators to NL, and append NL
|
||||||
|
* if the file was non-empty and didn't already end with one.
|
||||||
|
*
|
||||||
|
* {@see StreamVacuum#run()} for why this method exists.
|
||||||
|
*
|
||||||
|
* Returns {@code null} if the file does not exist or the output
|
||||||
|
* was empty.
|
||||||
|
*/
|
||||||
|
public static String read(Path path) throws IOException {
|
||||||
|
// Mimic StreamVacuum.run()'s behavior of replacing all platform-specific
|
||||||
|
// EOL sequences with NL.
|
||||||
|
StringBuilder buf = new StringBuilder();
|
||||||
|
try (BufferedReader in = Files.newBufferedReader(path, StandardCharsets.UTF_8)) {
|
||||||
|
append(in, buf);
|
||||||
|
} catch (FileNotFoundException | NoSuchFileException e) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (buf.length() > 0) {
|
||||||
|
return buf.toString();
|
||||||
|
} else {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -36,6 +36,7 @@ import org.antlr.v4.runtime.tree.ParseTree;
|
||||||
import org.antlr.v4.semantics.SemanticPipeline;
|
import org.antlr.v4.semantics.SemanticPipeline;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.DOTGenerator;
|
import org.antlr.v4.tool.DOTGenerator;
|
||||||
import org.antlr.v4.tool.Grammar;
|
import org.antlr.v4.tool.Grammar;
|
||||||
|
@ -46,13 +47,7 @@ import org.stringtemplate.v4.ST;
|
||||||
import org.stringtemplate.v4.STGroup;
|
import org.stringtemplate.v4.STGroup;
|
||||||
import org.stringtemplate.v4.STGroupString;
|
import org.stringtemplate.v4.STGroupString;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileWriter;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.lang.reflect.InvocationTargetException;
|
import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.net.URISyntaxException;
|
import java.net.URISyntaxException;
|
||||||
|
@ -70,6 +65,7 @@ import java.util.Set;
|
||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
@ -751,41 +747,6 @@ public class BaseCppTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader( new InputStreamReader(in) );
|
|
||||||
}
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line!=null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage)
|
GrammarSemanticsMessage expectedMessage)
|
||||||
throws Exception
|
throws Exception
|
||||||
|
@ -869,21 +830,6 @@ public class BaseCppTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(String dir) {
|
protected void mkdir(String dir) {
|
||||||
File f = new File(dir);
|
File f = new File(dir);
|
||||||
f.mkdirs();
|
f.mkdirs();
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.cpp;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseCppTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Cpp");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -10,9 +10,10 @@ import org.antlr.v4.runtime.CommonTokenStream;
|
||||||
import org.antlr.v4.runtime.Token;
|
import org.antlr.v4.runtime.Token;
|
||||||
import org.antlr.v4.runtime.TokenSource;
|
import org.antlr.v4.runtime.TokenSource;
|
||||||
import org.antlr.v4.runtime.WritableToken;
|
import org.antlr.v4.runtime.WritableToken;
|
||||||
import org.antlr.v4.runtime.misc.Utils;
|
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
|
import org.antlr.v4.test.runtime.TestOutputReading;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.GrammarSemanticsMessage;
|
import org.antlr.v4.tool.GrammarSemanticsMessage;
|
||||||
import org.junit.rules.TestRule;
|
import org.junit.rules.TestRule;
|
||||||
|
@ -31,7 +32,6 @@ import javax.xml.transform.stream.StreamResult;
|
||||||
import javax.xml.xpath.XPathConstants;
|
import javax.xml.xpath.XPathConstants;
|
||||||
import javax.xml.xpath.XPathExpression;
|
import javax.xml.xpath.XPathExpression;
|
||||||
import javax.xml.xpath.XPathFactory;
|
import javax.xml.xpath.XPathFactory;
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
@ -39,6 +39,7 @@ import java.io.InputStream;
|
||||||
import java.io.InputStreamReader;
|
import java.io.InputStreamReader;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
|
import java.nio.file.Path;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
@ -49,6 +50,7 @@ import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
import static org.junit.Assert.assertNotNull;
|
import static org.junit.Assert.assertNotNull;
|
||||||
import static org.junit.Assert.assertTrue;
|
import static org.junit.Assert.assertTrue;
|
||||||
|
@ -57,6 +59,12 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
public static final String newline = System.getProperty("line.separator");
|
public static final String newline = System.getProperty("line.separator");
|
||||||
public static final String pathSep = System.getProperty("path.separator");
|
public static final String pathSep = System.getProperty("path.separator");
|
||||||
|
|
||||||
|
/**
|
||||||
|
* When {@code true}, on Linux will call dotnet cli toolchain, otherwise
|
||||||
|
* will continue to use mono
|
||||||
|
*/
|
||||||
|
public static final boolean NETSTANDARD = Boolean.parseBoolean(System.getProperty("antlr-csharp-netstandard"));
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When the {@code antlr.preserve-test-dir} runtime property is set to
|
* When the {@code antlr.preserve-test-dir} runtime property is set to
|
||||||
* {@code true}, the temporary directories created by the test run will not
|
* {@code true}, the temporary directories created by the test run will not
|
||||||
|
@ -240,7 +248,7 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
return stderrDuringParse;
|
return stderrDuringParse;
|
||||||
}
|
}
|
||||||
String output = execTest();
|
String output = execTest();
|
||||||
if ( output.length()==0 ) {
|
if ( output!=null && output.length()==0 ) {
|
||||||
output = null;
|
output = null;
|
||||||
}
|
}
|
||||||
return output;
|
return output;
|
||||||
|
@ -351,15 +359,25 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean compile() {
|
public boolean compile() {
|
||||||
try {
|
if(!NETSTANDARD) {
|
||||||
if(!createProject())
|
try {
|
||||||
return false;
|
if(!createProject())
|
||||||
if(!buildProject())
|
return false;
|
||||||
return false;
|
if(!buildProject())
|
||||||
return true;
|
return false;
|
||||||
} catch(Exception e) {
|
return true;
|
||||||
return false;
|
} catch(Exception e) {
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
return createDotnetProject() && buildDotnetProject();
|
||||||
|
} catch(Exception e) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private File getTestProjectFile() {
|
private File getTestProjectFile() {
|
||||||
|
@ -405,11 +423,14 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
}
|
}
|
||||||
|
|
||||||
private String locateExec() {
|
private String locateExec() {
|
||||||
return new File(tmpdir, "bin/Release/Test.exe").getAbsolutePath();
|
if (!NETSTANDARD)
|
||||||
|
return new File(tmpdir, "bin/Release/Test.exe").getAbsolutePath();
|
||||||
|
|
||||||
|
return new File(tmpdir, "src/bin/Debug/netcoreapp1.0/Test.dll").getAbsolutePath();
|
||||||
}
|
}
|
||||||
|
|
||||||
private String locateTool(String tool) {
|
private String locateTool(String tool) {
|
||||||
String[] roots = { "/opt/local/bin/", "/usr/bin/", "/usr/local/bin/" };
|
String[] roots = { "/opt/local/bin/", "/usr/local/bin/", "/usr/bin/" };
|
||||||
for(String root : roots) {
|
for(String root : roots) {
|
||||||
if(new File(root + tool).exists())
|
if(new File(root + tool).exists())
|
||||||
return root + tool;
|
return root + tool;
|
||||||
|
@ -472,6 +493,105 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean createDotnetProject() {
|
||||||
|
try {
|
||||||
|
mkdir(tmpdir + "/src");
|
||||||
|
|
||||||
|
// move files to /src, since global.json need to be one level higher
|
||||||
|
File source = new File(tmpdir);
|
||||||
|
File[] files = source.listFiles();
|
||||||
|
for (File thisSource : files) {
|
||||||
|
if (!thisSource.isDirectory()) {
|
||||||
|
File thisDest = new File(tmpdir + "/src/" + thisSource.getName());
|
||||||
|
boolean success = thisSource.renameTo(thisDest);
|
||||||
|
|
||||||
|
if (!success) {
|
||||||
|
throw new RuntimeException("Moving file " + thisSource + " to " + thisDest + " failed.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// save auxiliary files
|
||||||
|
String pack = BaseCSharpTest.class.getPackage().getName().replace(".", "/") + "/";
|
||||||
|
saveResourceAsFile(pack + "global.json", new File(tmpdir, "global.json"));
|
||||||
|
saveResourceAsFile(pack + "project.json", new File(tmpdir, "src/project.json"));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
catch(Exception e) {
|
||||||
|
e.printStackTrace(System.err);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean buildDotnetProject() {
|
||||||
|
// find runtime package
|
||||||
|
final ClassLoader loader = Thread.currentThread().getContextClassLoader();
|
||||||
|
final URL runtimeProj = loader.getResource("CSharp/runtime/CSharp/Antlr4.Runtime/Antlr4.Runtime.dotnet.xproj");
|
||||||
|
if ( runtimeProj==null ) {
|
||||||
|
throw new RuntimeException("C# runtime project file not found!");
|
||||||
|
}
|
||||||
|
File runtimeProjFile = new File(runtimeProj.getFile());
|
||||||
|
String runtimeProjPath = runtimeProjFile.getParentFile().getParentFile().getPath();
|
||||||
|
String projectRefPath = runtimeProjPath.substring(0, runtimeProjPath.lastIndexOf("/"));
|
||||||
|
|
||||||
|
// update global.json to reference runtime path
|
||||||
|
try {
|
||||||
|
String content = new java.util.Scanner(new File(tmpdir + "/global.json")).useDelimiter("\\Z").next();
|
||||||
|
content = content.replaceAll("replace_this", projectRefPath);
|
||||||
|
java.io.PrintWriter out = new java.io.PrintWriter(tmpdir + "/global.json");
|
||||||
|
out.write(content);
|
||||||
|
out.close();
|
||||||
|
}
|
||||||
|
catch(Exception e) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// build test
|
||||||
|
String dotnetcli = locateTool("dotnet");
|
||||||
|
String[] args = new String[] {
|
||||||
|
dotnetcli,
|
||||||
|
"restore",
|
||||||
|
".",
|
||||||
|
projectRefPath
|
||||||
|
};
|
||||||
|
|
||||||
|
try {
|
||||||
|
boolean success = runProcess(args, tmpdir);
|
||||||
|
|
||||||
|
args = new String[] {
|
||||||
|
dotnetcli,
|
||||||
|
"build",
|
||||||
|
"src"
|
||||||
|
};
|
||||||
|
success = runProcess(args, tmpdir);
|
||||||
|
}
|
||||||
|
catch(Exception e) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean runProcess(String[] args, String path) throws Exception {
|
||||||
|
ProcessBuilder pb = new ProcessBuilder(args);
|
||||||
|
pb.directory(new File(path));
|
||||||
|
Process process = pb.start();
|
||||||
|
StreamVacuum stdoutVacuum = new StreamVacuum(process.getInputStream());
|
||||||
|
StreamVacuum stderrVacuum = new StreamVacuum(process.getErrorStream());
|
||||||
|
stdoutVacuum.start();
|
||||||
|
stderrVacuum.start();
|
||||||
|
process.waitFor();
|
||||||
|
stdoutVacuum.join();
|
||||||
|
stderrVacuum.join();
|
||||||
|
boolean success = process.exitValue()==0;
|
||||||
|
if ( !success ) {
|
||||||
|
this.stderrDuringParse = stderrVacuum.toString();
|
||||||
|
System.err.println("runProcess stderrVacuum: "+ this.stderrDuringParse);
|
||||||
|
}
|
||||||
|
return success;
|
||||||
|
}
|
||||||
|
|
||||||
private void saveResourceAsFile(String resourceName, File file) throws IOException {
|
private void saveResourceAsFile(String resourceName, File file) throws IOException {
|
||||||
InputStream input = Thread.currentThread().getContextClassLoader().getResourceAsStream(resourceName);
|
InputStream input = Thread.currentThread().getContextClassLoader().getResourceAsStream(resourceName);
|
||||||
if ( input==null ) {
|
if ( input==null ) {
|
||||||
|
@ -488,26 +608,18 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
|
|
||||||
public String execTest() {
|
public String execTest() {
|
||||||
String exec = locateExec();
|
String exec = locateExec();
|
||||||
String[] args = getExecTestArgs(exec);
|
|
||||||
try {
|
try {
|
||||||
|
File tmpdirFile = new File(tmpdir);
|
||||||
|
Path output = tmpdirFile.toPath().resolve("output");
|
||||||
|
Path errorOutput = tmpdirFile.toPath().resolve("error-output");
|
||||||
|
String[] args = getExecTestArgs(exec, output, errorOutput);
|
||||||
ProcessBuilder pb = new ProcessBuilder(args);
|
ProcessBuilder pb = new ProcessBuilder(args);
|
||||||
pb.directory(new File(tmpdir));
|
pb.directory(tmpdirFile);
|
||||||
Process process = pb.start();
|
Process process = pb.start();
|
||||||
StreamVacuum stdoutVacuum = new StreamVacuum(process.getInputStream());
|
|
||||||
StreamVacuum stderrVacuum = new StreamVacuum(process.getErrorStream());
|
|
||||||
stdoutVacuum.start();
|
|
||||||
stderrVacuum.start();
|
|
||||||
process.waitFor();
|
process.waitFor();
|
||||||
stdoutVacuum.join();
|
String writtenOutput = TestOutputReading.read(output);
|
||||||
stderrVacuum.join();
|
this.stderrDuringParse = TestOutputReading.read(errorOutput);
|
||||||
String output = stdoutVacuum.toString();
|
return writtenOutput;
|
||||||
if ( output.length()==0 ) {
|
|
||||||
output = null;
|
|
||||||
}
|
|
||||||
if ( stderrVacuum.toString().length()>0 ) {
|
|
||||||
this.stderrDuringParse = stderrVacuum.toString();
|
|
||||||
}
|
|
||||||
return output;
|
|
||||||
}
|
}
|
||||||
catch (Exception e) {
|
catch (Exception e) {
|
||||||
System.err.println("can't exec recognizer");
|
System.err.println("can't exec recognizer");
|
||||||
|
@ -516,12 +628,30 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private String[] getExecTestArgs(String exec) {
|
private String[] getExecTestArgs(String exec, Path output, Path errorOutput) {
|
||||||
if(isWindows())
|
if ( isWindows() ) {
|
||||||
return new String[] { exec, new File(tmpdir, "input").getAbsolutePath() } ;
|
return new String[]{
|
||||||
|
exec, new File(tmpdir, "input").getAbsolutePath(),
|
||||||
|
output.toAbsolutePath().toString(),
|
||||||
|
errorOutput.toAbsolutePath().toString()
|
||||||
|
};
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
String mono = locateTool("mono");
|
if (!NETSTANDARD) {
|
||||||
return new String[] { mono, exec, new File(tmpdir, "input").getAbsolutePath() };
|
String mono = locateTool("mono");
|
||||||
|
return new String[] {
|
||||||
|
mono, exec, new File(tmpdir, "input").getAbsolutePath(),
|
||||||
|
output.toAbsolutePath().toString(),
|
||||||
|
errorOutput.toAbsolutePath().toString()
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
String dotnet = locateTool("dotnet");
|
||||||
|
return new String[] {
|
||||||
|
dotnet, exec, new File(tmpdir, "src/input").getAbsolutePath(),
|
||||||
|
output.toAbsolutePath().toString(),
|
||||||
|
errorOutput.toAbsolutePath().toString()
|
||||||
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -534,41 +664,6 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader( new InputStreamReader(in) );
|
|
||||||
}
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line!=null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage)
|
GrammarSemanticsMessage expectedMessage)
|
||||||
throws Exception
|
throws Exception
|
||||||
|
@ -611,16 +706,6 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
Utils.writeFile(dir+"/"+fileName, content, "UTF-8");
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(String dir) {
|
protected void mkdir(String dir) {
|
||||||
File f = new File(dir);
|
File f = new File(dir);
|
||||||
f.mkdirs();
|
f.mkdirs();
|
||||||
|
@ -635,16 +720,23 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
"using System;\n" +
|
"using System;\n" +
|
||||||
"using Antlr4.Runtime;\n" +
|
"using Antlr4.Runtime;\n" +
|
||||||
"using Antlr4.Runtime.Tree;\n" +
|
"using Antlr4.Runtime.Tree;\n" +
|
||||||
|
"using System.IO;\n" +
|
||||||
|
"using System.Text;\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"public class Test {\n" +
|
"public class Test {\n" +
|
||||||
" public static void Main(string[] args) {\n" +
|
" public static void Main(string[] args) {\n" +
|
||||||
" ICharStream input = new AntlrFileStream(args[0]);\n" +
|
" string inputData = File.ReadAllText(args[0], Encoding.UTF8);\n" +
|
||||||
" <lexerName> lex = new <lexerName>(input);\n" +
|
" using (TextWriter output = new StreamWriter(args[1]),\n" +
|
||||||
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
" errorOutput = new StreamWriter(args[2])) {\n" +
|
||||||
" <createParser>\n"+
|
" CodePointCharStream input = new CodePointCharStream(inputData);\n" +
|
||||||
" parser.BuildParseTree = true;\n" +
|
" input.name = args[0];\n" +
|
||||||
" ParserRuleContext tree = parser.<parserStartRuleName>();\n" +
|
" <lexerName> lex = new <lexerName>(input, output, errorOutput);\n" +
|
||||||
" ParseTreeWalker.Default.Walk(new TreeShapeListener(), tree);\n" +
|
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
||||||
|
" <createParser>\n"+
|
||||||
|
" parser.BuildParseTree = true;\n" +
|
||||||
|
" ParserRuleContext tree = parser.<parserStartRuleName>();\n" +
|
||||||
|
" ParseTreeWalker.Default.Walk(new TreeShapeListener(), tree);\n" +
|
||||||
|
" }\n" +
|
||||||
" }\n" +
|
" }\n" +
|
||||||
"}\n" +
|
"}\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
|
@ -663,11 +755,11 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
" }\n" +
|
" }\n" +
|
||||||
"}"
|
"}"
|
||||||
);
|
);
|
||||||
ST createParserST = new ST(" <parserName> parser = new <parserName>(tokens);\n");
|
ST createParserST = new ST(" <parserName> parser = new <parserName>(tokens, output, errorOutput);\n");
|
||||||
if ( debug ) {
|
if ( debug ) {
|
||||||
createParserST =
|
createParserST =
|
||||||
new ST(
|
new ST(
|
||||||
" <parserName> parser = new <parserName>(tokens);\n" +
|
" <parserName> parser = new <parserName>(tokens, output, errorOutput);\n" +
|
||||||
" parser.AddErrorListener(new DiagnosticErrorListener());\n");
|
" parser.AddErrorListener(new DiagnosticErrorListener());\n");
|
||||||
}
|
}
|
||||||
outputFileST.add("createParser", createParserST);
|
outputFileST.add("createParser", createParserST);
|
||||||
|
@ -681,17 +773,23 @@ public class BaseCSharpTest implements RuntimeTestSupport /*, SpecialRuntimeTest
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
"using System;\n" +
|
"using System;\n" +
|
||||||
"using Antlr4.Runtime;\n" +
|
"using Antlr4.Runtime;\n" +
|
||||||
|
"using System.IO;\n" +
|
||||||
|
"using System.Text;\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"public class Test {\n" +
|
"public class Test {\n" +
|
||||||
" public static void Main(string[] args) {\n" +
|
" public static void Main(string[] args) {\n" +
|
||||||
" ICharStream input = new AntlrFileStream(args[0]);\n" +
|
" string inputData = File.ReadAllText(args[0], Encoding.UTF8);\n" +
|
||||||
" <lexerName> lex = new <lexerName>(input);\n" +
|
" ICharStream input = new CodePointCharStream(inputData);\n" +
|
||||||
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
" using (TextWriter output = new StreamWriter(args[1]),\n" +
|
||||||
" tokens.Fill();\n" +
|
" errorOutput = new StreamWriter(args[2])) {\n" +
|
||||||
" foreach (object t in tokens.GetTokens())\n" +
|
" <lexerName> lex = new <lexerName>(input, output, errorOutput);\n" +
|
||||||
" Console.WriteLine(t);\n" +
|
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
||||||
(showDFA?" Console.Write(lex.Interpreter.GetDFA(Lexer.DEFAULT_MODE).ToLexerString());\n":"")+
|
" tokens.Fill();\n" +
|
||||||
" }\n" +
|
" foreach (object t in tokens.GetTokens())\n" +
|
||||||
|
" output.WriteLine(t);\n" +
|
||||||
|
(showDFA?" output.Write(lex.Interpreter.GetDFA(Lexer.DEFAULT_MODE).ToLexerString());\n":"")+
|
||||||
|
" }\n" +
|
||||||
|
"}\n" +
|
||||||
"}"
|
"}"
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.csharp;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseCSharpTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "CSharp");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
{
|
||||||
|
"projects": [
|
||||||
|
"replace_this"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,27 @@
|
||||||
|
{
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"frameworks": {
|
||||||
|
"netcoreapp1.0": {
|
||||||
|
"imports": [
|
||||||
|
"dnxcore50"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.NETCore.App": {
|
||||||
|
"type": "platform",
|
||||||
|
"version": "1.1.0"
|
||||||
|
},
|
||||||
|
"CSharp": {
|
||||||
|
"target": "Project",
|
||||||
|
"version": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"buildOptions": {
|
||||||
|
"emitEntryPoint": true,
|
||||||
|
"outputName": "Test",
|
||||||
|
"nowarn": [
|
||||||
|
"CS3021"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
|
@ -112,7 +112,7 @@ public class ParseTreesDescriptors {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean ignore(String targetName) {
|
public boolean ignore(String targetName) {
|
||||||
return !targetName.matches("Java|Python2|Python3|Node|Swift");
|
return !targetName.matches("Java|Python2|Python3|Node|Swift|CSharp");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -135,7 +135,7 @@ public class ParserErrorsDescriptors {
|
||||||
public static class InvalidEmptyInput extends BaseParserTestDescriptor {
|
public static class InvalidEmptyInput extends BaseParserTestDescriptor {
|
||||||
public String input = "";
|
public String input = "";
|
||||||
public String output = null;
|
public String output = null;
|
||||||
public String errors = "line 1:0 missing ID at '<EOF>'\n";
|
public String errors = "line 1:0 mismatched input '<EOF>' expecting ID\n";
|
||||||
public String startRule = "start";
|
public String startRule = "start";
|
||||||
public String grammarName = "T";
|
public String grammarName = "T";
|
||||||
|
|
||||||
|
@ -414,7 +414,7 @@ public class ParserErrorsDescriptors {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
grammar T;
|
grammar T;
|
||||||
a : 'a' 'b'* ;
|
a : 'a' 'b'* EOF ;
|
||||||
*/
|
*/
|
||||||
@CommentHasStringValue
|
@CommentHasStringValue
|
||||||
public String grammar;
|
public String grammar;
|
||||||
|
@ -436,7 +436,7 @@ public class ParserErrorsDescriptors {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
grammar T;
|
grammar T;
|
||||||
a : 'a' ('b'|'z'{<Pass()>})*;
|
a : 'a' ('b'|'z'{<Pass()>})* EOF ;
|
||||||
*/
|
*/
|
||||||
@CommentHasStringValue
|
@CommentHasStringValue
|
||||||
public String grammar;
|
public String grammar;
|
||||||
|
|
|
@ -753,6 +753,83 @@ public class ParserExecDescriptors {
|
||||||
*/
|
*/
|
||||||
@CommentHasStringValue
|
@CommentHasStringValue
|
||||||
public String grammar;
|
public String grammar;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is a regression test for antlr/antlr4#1545, case 1.
|
||||||
|
*/
|
||||||
|
public static class OpenDeviceStatement_Case1 extends BaseParserTestDescriptor {
|
||||||
|
public String input = "OPEN DEVICE DEVICE";
|
||||||
|
public String output = "OPEN DEVICE DEVICE\n";
|
||||||
|
public String errors = null;
|
||||||
|
public String startRule = "statement";
|
||||||
|
public String grammarName = "OpenDeviceStatement";
|
||||||
|
|
||||||
|
/**
|
||||||
|
grammar OpenDeviceStatement;
|
||||||
|
program : statement+ '.' ;
|
||||||
|
|
||||||
|
statement : 'OPEN' ( 'DEVICE' ( OPT1 | OPT2 | OPT3 )? )+ {<writeln("$text")>} ;
|
||||||
|
|
||||||
|
OPT1 : 'OPT-1';
|
||||||
|
OPT2 : 'OPT-2';
|
||||||
|
OPT3 : 'OPT-3';
|
||||||
|
|
||||||
|
WS : (' '|'\n')+ -> channel(HIDDEN);
|
||||||
|
*/
|
||||||
|
@CommentHasStringValue
|
||||||
|
public String grammar;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is a regression test for antlr/antlr4#1545, case 2.
|
||||||
|
*/
|
||||||
|
public static class OpenDeviceStatement_Case2 extends BaseParserTestDescriptor {
|
||||||
|
public String input = "OPEN DEVICE DEVICE";
|
||||||
|
public String output = "OPEN DEVICE DEVICE\n";
|
||||||
|
public String errors = null;
|
||||||
|
public String startRule = "statement";
|
||||||
|
public String grammarName = "OpenDeviceStatement";
|
||||||
|
|
||||||
|
/**
|
||||||
|
grammar OpenDeviceStatement;
|
||||||
|
program : statement+ '.' ;
|
||||||
|
|
||||||
|
statement : 'OPEN' ( 'DEVICE' ( (OPT1) | OPT2 | OPT3 )? )+ {<writeln("$text")>} ;
|
||||||
|
|
||||||
|
OPT1 : 'OPT-1';
|
||||||
|
OPT2 : 'OPT-2';
|
||||||
|
OPT3 : 'OPT-3';
|
||||||
|
|
||||||
|
WS : (' '|'\n')+ -> channel(HIDDEN);
|
||||||
|
*/
|
||||||
|
@CommentHasStringValue
|
||||||
|
public String grammar;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is a regression test for antlr/antlr4#1545, case 3.
|
||||||
|
*/
|
||||||
|
public static class OpenDeviceStatement_Case3 extends BaseParserTestDescriptor {
|
||||||
|
public String input = "OPEN DEVICE DEVICE.";
|
||||||
|
public String output = "OPEN DEVICE DEVICE\n";
|
||||||
|
public String errors = null;
|
||||||
|
public String startRule = "statement";
|
||||||
|
public String grammarName = "OpenDeviceStatement";
|
||||||
|
|
||||||
|
/**
|
||||||
|
grammar OpenDeviceStatement;
|
||||||
|
program : statement+ '.' ;
|
||||||
|
|
||||||
|
statement : 'OPEN' ( 'DEVICE' ( (OPT1) | OPT2 | OPT3 )? )+ {<writeln("$text")>} ;
|
||||||
|
|
||||||
|
OPT1 : 'OPT-1';
|
||||||
|
OPT2 : 'OPT-2';
|
||||||
|
OPT3 : 'OPT-3';
|
||||||
|
|
||||||
|
WS : (' '|'\n')+ -> channel(HIDDEN);
|
||||||
|
*/
|
||||||
|
@CommentHasStringValue
|
||||||
|
public String grammar;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -113,7 +113,7 @@ public class PerformanceDescriptors {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean ignore(String targetName) {
|
public boolean ignore(String targetName) {
|
||||||
return !Arrays.asList("Java", "CSharp", "Python2", "Python3", "Node").contains(targetName);
|
return !Arrays.asList("Java", "CSharp", "Python2", "Python3", "Node", "Cpp").contains(targetName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -199,7 +199,7 @@ public class PerformanceDescriptors {
|
||||||
@Override
|
@Override
|
||||||
public boolean ignore(String targetName) {
|
public boolean ignore(String targetName) {
|
||||||
// passes, but still too slow in Python and JavaScript
|
// passes, but still too slow in Python and JavaScript
|
||||||
return !Arrays.asList("Java", "CSharp").contains(targetName);
|
return !Arrays.asList("Java", "CSharp", "Cpp").contains(targetName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,273 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.descriptors;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseParserTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.CommentHasStringValue;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.JavaScriptTargets;
|
|
||||||
|
|
||||||
public class VisitorsDescriptors {
|
|
||||||
public static boolean isJavaScriptTarget(String targetName) {
|
|
||||||
boolean isJavaScriptTarget = Arrays.binarySearch(JavaScriptTargets, targetName)>=0;
|
|
||||||
return isJavaScriptTarget;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class Basic extends BaseParserTestDescriptor {
|
|
||||||
public String input = "1 2";
|
|
||||||
/**
|
|
||||||
(a 1 2)
|
|
||||||
[ '1', '2' ]
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
|
|
||||||
public String errors = null;
|
|
||||||
public String startRule = "s";
|
|
||||||
public String grammarName = "T";
|
|
||||||
|
|
||||||
/**
|
|
||||||
grammar T;
|
|
||||||
@parser::header {
|
|
||||||
<ImportVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
@parser::members {
|
|
||||||
<BasicVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
s
|
|
||||||
@after {
|
|
||||||
<ToStringTree("$ctx.r"):writeln()>
|
|
||||||
<WalkVisitor("$ctx.r")>
|
|
||||||
}
|
|
||||||
: r=a ;
|
|
||||||
a : INT INT
|
|
||||||
| ID
|
|
||||||
;
|
|
||||||
MULT: '*' ;
|
|
||||||
ADD : '+' ;
|
|
||||||
INT : [0-9]+ ;
|
|
||||||
ID : [a-z]+ ;
|
|
||||||
WS : [ \t\n]+ -> skip ;
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String grammar;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean ignore(String targetName) { return !isJavaScriptTarget(targetName); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class LR extends BaseParserTestDescriptor {
|
|
||||||
public String input = "1+2*3";
|
|
||||||
/**
|
|
||||||
(e (e 1) + (e (e 2) * (e 3)))
|
|
||||||
1,,2,,32 3 21 2 1
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
|
|
||||||
public String errors = null;
|
|
||||||
public String startRule = "s";
|
|
||||||
public String grammarName = "T";
|
|
||||||
|
|
||||||
/**
|
|
||||||
grammar T;
|
|
||||||
@parser::header {
|
|
||||||
<ImportVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
@parser::members {
|
|
||||||
<LRVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
s
|
|
||||||
@after {
|
|
||||||
<ToStringTree("$ctx.r"):writeln()>
|
|
||||||
<WalkVisitor("$ctx.r")>
|
|
||||||
}
|
|
||||||
: r=e ;
|
|
||||||
e : e op='*' e
|
|
||||||
| e op='+' e
|
|
||||||
| INT
|
|
||||||
;
|
|
||||||
MULT: '*' ;
|
|
||||||
ADD : '+' ;
|
|
||||||
INT : [0-9]+ ;
|
|
||||||
ID : [a-z]+ ;
|
|
||||||
WS : [ \t\n]+ -> skip ;
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String grammar;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean ignore(String targetName) { return !isJavaScriptTarget(targetName); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class LRWithLabels extends BaseParserTestDescriptor {
|
|
||||||
public String input = "1(2,3)";
|
|
||||||
/**
|
|
||||||
(e (e 1) ( (eList (e 2) , (e 3)) ))
|
|
||||||
1,,2,,3,1 [13 6]
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
|
|
||||||
public String errors = null;
|
|
||||||
public String startRule = "s";
|
|
||||||
public String grammarName = "T";
|
|
||||||
|
|
||||||
/**
|
|
||||||
grammar T;
|
|
||||||
@parser::header {
|
|
||||||
<ImportVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
@parser::members {
|
|
||||||
<LRWithLabelsVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
s
|
|
||||||
@after {
|
|
||||||
<ToStringTree("$ctx.r"):writeln()>
|
|
||||||
<WalkVisitor("$ctx.r")>
|
|
||||||
}
|
|
||||||
: r=e ;
|
|
||||||
e : e '(' eList ')' # Call
|
|
||||||
| INT # Int
|
|
||||||
;
|
|
||||||
eList : e (',' e)* ;
|
|
||||||
MULT: '*' ;
|
|
||||||
ADD : '+' ;
|
|
||||||
INT : [0-9]+ ;
|
|
||||||
ID : [a-z]+ ;
|
|
||||||
WS : [ \t\n]+ -> skip ;
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String grammar;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean ignore(String targetName) { return !isJavaScriptTarget(targetName); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static abstract class RuleGetters extends BaseParserTestDescriptor {
|
|
||||||
public String errors = null;
|
|
||||||
public String startRule = "s";
|
|
||||||
public String grammarName = "T";
|
|
||||||
|
|
||||||
/**
|
|
||||||
grammar T;
|
|
||||||
@parser::header {
|
|
||||||
<ImportVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
@parser::members {
|
|
||||||
<RuleGetterVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
s
|
|
||||||
@after {
|
|
||||||
<ToStringTree("$ctx.r"):writeln()>
|
|
||||||
<WalkVisitor("$ctx.r")>
|
|
||||||
}
|
|
||||||
: r=a ;
|
|
||||||
a : b b // forces list
|
|
||||||
| b // a list still
|
|
||||||
;
|
|
||||||
b : ID | INT;
|
|
||||||
MULT: '*' ;
|
|
||||||
ADD : '+' ;
|
|
||||||
INT : [0-9]+ ;
|
|
||||||
ID : [a-z]+ ;
|
|
||||||
WS : [ \t\n]+ -> skip ;
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String grammar;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean ignore(String targetName) { return !isJavaScriptTarget(targetName); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class RuleGetters_1 extends RuleGetters {
|
|
||||||
public String input = "1 2";
|
|
||||||
/**
|
|
||||||
(a (b 1) (b 2))
|
|
||||||
,1 2 1
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class RuleGetters_2 extends RuleGetters {
|
|
||||||
public String input = "abc";
|
|
||||||
/**
|
|
||||||
(a (b abc))
|
|
||||||
abc
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static abstract class TokenGetters extends BaseParserTestDescriptor {
|
|
||||||
public String errors = null;
|
|
||||||
public String startRule = "s";
|
|
||||||
public String grammarName = "T";
|
|
||||||
|
|
||||||
/**
|
|
||||||
grammar T;
|
|
||||||
@parser::header {
|
|
||||||
<ImportVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
@parser::members {
|
|
||||||
<TokenGetterVisitor(grammarName)>
|
|
||||||
}
|
|
||||||
|
|
||||||
s
|
|
||||||
@after {
|
|
||||||
<ToStringTree("$ctx.r"):writeln()>
|
|
||||||
<WalkVisitor("$ctx.r")>
|
|
||||||
}
|
|
||||||
: r=a ;
|
|
||||||
a : INT INT
|
|
||||||
| ID
|
|
||||||
;
|
|
||||||
MULT: '*' ;
|
|
||||||
ADD : '+' ;
|
|
||||||
INT : [0-9]+ ;
|
|
||||||
ID : [a-z]+ ;
|
|
||||||
WS : [ \t\n]+ -> skip ;
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String grammar;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean ignore(String targetName) { return !isJavaScriptTarget(targetName); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class TokenGetters_1 extends TokenGetters {
|
|
||||||
public String input = "1 2";
|
|
||||||
/**
|
|
||||||
(a 1 2)
|
|
||||||
,1 2 [1, 2]
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class TokenGetters_2 extends TokenGetters {
|
|
||||||
public String input = "abc";
|
|
||||||
/**
|
|
||||||
(a abc)
|
|
||||||
[@0,0:2='abc',<4>,1:0]
|
|
||||||
*/
|
|
||||||
@CommentHasStringValue
|
|
||||||
public String output;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -33,6 +33,7 @@ import org.antlr.v4.runtime.misc.Interval;
|
||||||
import org.antlr.v4.semantics.SemanticPipeline;
|
import org.antlr.v4.semantics.SemanticPipeline;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.DOTGenerator;
|
import org.antlr.v4.tool.DOTGenerator;
|
||||||
import org.antlr.v4.tool.Grammar;
|
import org.antlr.v4.tool.Grammar;
|
||||||
|
@ -43,8 +44,6 @@ import org.stringtemplate.v4.ST;
|
||||||
import org.stringtemplate.v4.STGroup;
|
import org.stringtemplate.v4.STGroup;
|
||||||
import org.stringtemplate.v4.STGroupString;
|
import org.stringtemplate.v4.STGroupString;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileFilter;
|
import java.io.FileFilter;
|
||||||
import java.io.FileInputStream;
|
import java.io.FileInputStream;
|
||||||
|
@ -52,7 +51,6 @@ import java.io.FileOutputStream;
|
||||||
import java.io.FileWriter;
|
import java.io.FileWriter;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
@ -70,6 +68,7 @@ import static junit.framework.TestCase.assertFalse;
|
||||||
import static junit.framework.TestCase.assertNotNull;
|
import static junit.framework.TestCase.assertNotNull;
|
||||||
import static junit.framework.TestCase.assertTrue;
|
import static junit.framework.TestCase.assertTrue;
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
|
|
||||||
public class BaseGoTest implements RuntimeTestSupport {
|
public class BaseGoTest implements RuntimeTestSupport {
|
||||||
|
@ -309,7 +308,7 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
boolean success = rawGenerateAndBuildRecognizer(grammarFileName,
|
boolean success = rawGenerateAndBuildRecognizer(grammarFileName,
|
||||||
grammarStr, null, lexerName, "-no-listener");
|
grammarStr, null, lexerName, "-no-listener");
|
||||||
assertTrue(success);
|
assertTrue(success);
|
||||||
writeFile(overall_tmpdir, "input", input);
|
writeFile(overall_tmpdir.toString(), "input", input);
|
||||||
writeLexerTestFile(lexerName, showDFA);
|
writeLexerTestFile(lexerName, showDFA);
|
||||||
String output = execModule("Test.go");
|
String output = execModule("Test.go");
|
||||||
return output;
|
return output;
|
||||||
|
@ -338,7 +337,7 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
boolean success = rawGenerateAndBuildRecognizer(grammarFileName,
|
boolean success = rawGenerateAndBuildRecognizer(grammarFileName,
|
||||||
grammarStr, parserName, lexerName, "-visitor");
|
grammarStr, parserName, lexerName, "-visitor");
|
||||||
assertTrue(success);
|
assertTrue(success);
|
||||||
writeFile(overall_tmpdir, "input", input);
|
writeFile(overall_tmpdir.toString(), "input", input);
|
||||||
rawBuildRecognizerTestFile(parserName, lexerName, listenerName,
|
rawBuildRecognizerTestFile(parserName, lexerName, listenerName,
|
||||||
visitorName, startRuleName, showDiagnosticErrors);
|
visitorName, startRuleName, showDiagnosticErrors);
|
||||||
return execRecognizer();
|
return execRecognizer();
|
||||||
|
@ -571,45 +570,6 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader(new InputStreamReader(in));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line != null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage) throws Exception {
|
GrammarSemanticsMessage expectedMessage) throws Exception {
|
||||||
ANTLRMessage foundMsg = null;
|
ANTLRMessage foundMsg = null;
|
||||||
|
@ -700,35 +660,6 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(File dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, InputStream content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
OutputStream output = new FileOutputStream(f);
|
|
||||||
while(content.available()>0) {
|
|
||||||
int b = content.read();
|
|
||||||
output.write(b);
|
|
||||||
}
|
|
||||||
output.close();
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(File dir) {
|
protected void mkdir(File dir) {
|
||||||
dir.mkdirs();
|
dir.mkdirs();
|
||||||
}
|
}
|
||||||
|
@ -785,7 +716,7 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
outputFileST.add("listenerName", listenerName);
|
outputFileST.add("listenerName", listenerName);
|
||||||
outputFileST.add("visitorName", visitorName);
|
outputFileST.add("visitorName", visitorName);
|
||||||
outputFileST.add("parserStartRuleName", parserStartRuleName.substring(0, 1).toUpperCase() + parserStartRuleName.substring(1) );
|
outputFileST.add("parserStartRuleName", parserStartRuleName.substring(0, 1).toUpperCase() + parserStartRuleName.substring(1) );
|
||||||
writeFile(overall_tmpdir, "Test.go", outputFileST.render());
|
writeFile(overall_tmpdir.toString(), "Test.go", outputFileST.render());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -813,7 +744,7 @@ public class BaseGoTest implements RuntimeTestSupport {
|
||||||
+ "}\n"
|
+ "}\n"
|
||||||
+ "\n");
|
+ "\n");
|
||||||
outputFileST.add("lexerName", lexerName);
|
outputFileST.add("lexerName", lexerName);
|
||||||
writeFile(overall_tmpdir, "Test.go", outputFileST.render());
|
writeFile(overall_tmpdir.toString(), "Test.go", outputFileST.render());
|
||||||
}
|
}
|
||||||
|
|
||||||
public void writeRecognizer(String parserName, String lexerName,
|
public void writeRecognizer(String parserName, String lexerName,
|
||||||
|
|
|
@ -1,33 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.go;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.AfterClass;
|
|
||||||
import org.junit.BeforeClass;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseGoTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@BeforeClass
|
|
||||||
public static void groupSetUp() throws Exception { BaseGoTest.groupSetUp(); }
|
|
||||||
|
|
||||||
@AfterClass
|
|
||||||
public static void groupTearDown() throws Exception { BaseGoTest.groupTearDown(); }
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Go");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -40,6 +40,7 @@ import org.antlr.v4.semantics.SemanticPipeline;
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.Grammar;
|
import org.antlr.v4.tool.Grammar;
|
||||||
import org.antlr.v4.tool.GrammarSemanticsMessage;
|
import org.antlr.v4.tool.GrammarSemanticsMessage;
|
||||||
|
@ -53,7 +54,6 @@ import javax.tools.JavaCompiler;
|
||||||
import javax.tools.JavaFileObject;
|
import javax.tools.JavaFileObject;
|
||||||
import javax.tools.StandardJavaFileManager;
|
import javax.tools.StandardJavaFileManager;
|
||||||
import javax.tools.ToolProvider;
|
import javax.tools.ToolProvider;
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
@ -81,6 +81,7 @@ import static junit.framework.TestCase.assertEquals;
|
||||||
import static junit.framework.TestCase.assertFalse;
|
import static junit.framework.TestCase.assertFalse;
|
||||||
import static junit.framework.TestCase.assertNotNull;
|
import static junit.framework.TestCase.assertNotNull;
|
||||||
import static junit.framework.TestCase.assertTrue;
|
import static junit.framework.TestCase.assertTrue;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
|
|
||||||
public class BaseJavaTest implements RuntimeTestSupport {
|
public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
|
@ -702,6 +703,7 @@ public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
try {
|
try {
|
||||||
String[] args = new String[] {
|
String[] args = new String[] {
|
||||||
"java", "-classpath", tmpdir+pathSep+CLASSPATH,
|
"java", "-classpath", tmpdir+pathSep+CLASSPATH,
|
||||||
|
"-Dfile.encoding=UTF-8",
|
||||||
className, new File(tmpdir, "input").getAbsolutePath()
|
className, new File(tmpdir, "input").getAbsolutePath()
|
||||||
};
|
};
|
||||||
// String cmdLine = Utils.join(args, " ");
|
// String cmdLine = Utils.join(args, " ");
|
||||||
|
@ -823,41 +825,6 @@ public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader( new InputStreamReader(in) );
|
|
||||||
}
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line!=null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage)
|
GrammarSemanticsMessage expectedMessage)
|
||||||
throws Exception
|
throws Exception
|
||||||
|
@ -941,16 +908,6 @@ public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
Utils.writeFile(dir+"/"+fileName, content, "UTF-8");
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void writeTestFile(String parserName,
|
protected void writeTestFile(String parserName,
|
||||||
String lexerName,
|
String lexerName,
|
||||||
String parserStartRuleName,
|
String parserStartRuleName,
|
||||||
|
@ -961,11 +918,12 @@ public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
"import org.antlr.v4.runtime.*;\n" +
|
"import org.antlr.v4.runtime.*;\n" +
|
||||||
"import org.antlr.v4.runtime.tree.*;\n" +
|
"import org.antlr.v4.runtime.tree.*;\n" +
|
||||||
"import org.antlr.v4.runtime.atn.*;\n" +
|
"import org.antlr.v4.runtime.atn.*;\n" +
|
||||||
|
"import java.nio.file.Paths;\n"+
|
||||||
"import java.util.Arrays;\n"+
|
"import java.util.Arrays;\n"+
|
||||||
"\n" +
|
"\n" +
|
||||||
"public class Test {\n" +
|
"public class Test {\n" +
|
||||||
" public static void main(String[] args) throws Exception {\n" +
|
" public static void main(String[] args) throws Exception {\n" +
|
||||||
" CharStream input = new ANTLRFileStream(args[0]);\n" +
|
" CharStream input = CharStreams.createWithUTF8(Paths.get(args[0]));\n" +
|
||||||
" <lexerName> lex = new <lexerName>(input);\n" +
|
" <lexerName> lex = new <lexerName>(input);\n" +
|
||||||
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
||||||
" <createParser>\n"+
|
" <createParser>\n"+
|
||||||
|
@ -1017,11 +975,12 @@ public class BaseJavaTest implements RuntimeTestSupport {
|
||||||
|
|
||||||
protected void writeLexerTestFile(String lexerName, boolean showDFA) {
|
protected void writeLexerTestFile(String lexerName, boolean showDFA) {
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
|
"import java.nio.file.Paths;\n" +
|
||||||
"import org.antlr.v4.runtime.*;\n" +
|
"import org.antlr.v4.runtime.*;\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"public class Test {\n" +
|
"public class Test {\n" +
|
||||||
" public static void main(String[] args) throws Exception {\n" +
|
" public static void main(String[] args) throws Exception {\n" +
|
||||||
" CharStream input = new ANTLRFileStream(args[0]);\n" +
|
" CharStream input = CharStreams.createWithUTF8(Paths.get(args[0]));\n" +
|
||||||
" <lexerName> lex = new <lexerName>(input);\n" +
|
" <lexerName> lex = new <lexerName>(input);\n" +
|
||||||
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
" CommonTokenStream tokens = new CommonTokenStream(lex);\n" +
|
||||||
" tokens.fill();\n" +
|
" tokens.fill();\n" +
|
||||||
|
|
|
@ -0,0 +1,172 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime.java;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
|
||||||
|
import java.nio.channels.SeekableByteChannel;
|
||||||
|
import java.nio.charset.CharacterCodingException;
|
||||||
|
import java.nio.charset.CodingErrorAction;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.nio.file.Files;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.CharStreams;
|
||||||
|
import org.antlr.v4.runtime.CodePointCharStream;
|
||||||
|
|
||||||
|
import org.junit.Rule;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.rules.ExpectedException;
|
||||||
|
import org.junit.rules.TemporaryFolder;
|
||||||
|
|
||||||
|
public class TestCharStreams {
|
||||||
|
@Rule
|
||||||
|
public TemporaryFolder folder = new TemporaryFolder();
|
||||||
|
|
||||||
|
@Rule
|
||||||
|
public ExpectedException thrown = ExpectedException.none();
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithBMPStringHasExpectedSize() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("hello");
|
||||||
|
assertEquals(5, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello", s.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithSMPStringHasExpectedSize() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
"hello \uD83C\uDF0E");
|
||||||
|
assertEquals(7, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello \uD83C\uDF0E", s.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithBMPUTF8PathHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello".getBytes(StandardCharsets.UTF_8));
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8(p);
|
||||||
|
assertEquals(5, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello", s.toString());
|
||||||
|
assertEquals(p.toString(), s.getSourceName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithSMPUTF8PathHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello \uD83C\uDF0E".getBytes(StandardCharsets.UTF_8));
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8(p);
|
||||||
|
assertEquals(7, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello \uD83C\uDF0E", s.toString());
|
||||||
|
assertEquals(p.toString(), s.getSourceName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithBMPUTF8InputStreamHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello".getBytes(StandardCharsets.UTF_8));
|
||||||
|
try (InputStream is = Files.newInputStream(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Stream(is);
|
||||||
|
assertEquals(5, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello", s.toString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithSMPUTF8InputStreamHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello \uD83C\uDF0E".getBytes(StandardCharsets.UTF_8));
|
||||||
|
try (InputStream is = Files.newInputStream(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Stream(is);
|
||||||
|
assertEquals(7, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello \uD83C\uDF0E", s.toString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithBMPUTF8ChannelHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello".getBytes(StandardCharsets.UTF_8));
|
||||||
|
try (SeekableByteChannel c = Files.newByteChannel(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Channel(
|
||||||
|
c, 4096, CodingErrorAction.REPLACE, "foo");
|
||||||
|
assertEquals(5, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello", s.toString());
|
||||||
|
assertEquals("foo", s.getSourceName());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithSMPUTF8ChannelHasExpectedSize() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello \uD83C\uDF0E".getBytes(StandardCharsets.UTF_8));
|
||||||
|
try (SeekableByteChannel c = Files.newByteChannel(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Channel(
|
||||||
|
c, 4096, CodingErrorAction.REPLACE, "foo");
|
||||||
|
assertEquals(7, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello \uD83C\uDF0E", s.toString());
|
||||||
|
assertEquals("foo", s.getSourceName());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithInvalidUTF8BytesChannelReplacesWithSubstCharInReplaceMode()
|
||||||
|
throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
byte[] toWrite = new byte[] { (byte)0xCA, (byte)0xFE, (byte)0xFE, (byte)0xED };
|
||||||
|
Files.write(p, toWrite);
|
||||||
|
try (SeekableByteChannel c = Files.newByteChannel(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Channel(
|
||||||
|
c, 4096, CodingErrorAction.REPLACE, "foo");
|
||||||
|
assertEquals(3, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("\uFFFD\uFFFD\uFFFD", s.toString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithInvalidUTF8BytesThrowsInReportMode() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
byte[] toWrite = new byte[] { (byte)0xCA, (byte)0xFE };
|
||||||
|
Files.write(p, toWrite);
|
||||||
|
try (SeekableByteChannel c = Files.newByteChannel(p)) {
|
||||||
|
thrown.expect(CharacterCodingException.class);
|
||||||
|
CharStreams.createWithUTF8Channel(c, 4096, CodingErrorAction.REPORT, "foo");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createWithSMPUTF8SequenceStraddlingBufferBoundary() throws Exception {
|
||||||
|
Path p = folder.newFile().toPath();
|
||||||
|
Files.write(p, "hello \uD83C\uDF0E".getBytes(StandardCharsets.UTF_8));
|
||||||
|
try (SeekableByteChannel c = Files.newByteChannel(p)) {
|
||||||
|
CodePointCharStream s = CharStreams.createWithUTF8Channel(
|
||||||
|
c,
|
||||||
|
// Note this buffer size ensures the SMP code point
|
||||||
|
// straddles the boundary of two buffers
|
||||||
|
8,
|
||||||
|
CodingErrorAction.REPLACE,
|
||||||
|
"foo");
|
||||||
|
assertEquals(7, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals("hello \uD83C\uDF0E", s.toString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,294 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime.java;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.IntBuffer;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.CharStreams;
|
||||||
|
import org.antlr.v4.runtime.CodePointCharStream;
|
||||||
|
import org.antlr.v4.runtime.IntStream;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.misc.Interval;
|
||||||
|
|
||||||
|
import org.junit.Rule;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
||||||
|
public class TestCodePointCharStream {
|
||||||
|
@Rule
|
||||||
|
public ExpectedException thrown = ExpectedException.none();
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void emptyBytesHasSize0() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("");
|
||||||
|
assertEquals(0, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void emptyBytesLookAheadReturnsEOF() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("");
|
||||||
|
assertEquals(IntStream.EOF, s.LA(1));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingEmptyStreamShouldThrow() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("");
|
||||||
|
thrown.expect(IllegalStateException.class);
|
||||||
|
thrown.expectMessage("cannot consume EOF");
|
||||||
|
s.consume();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleLatinCodePointHasSize1() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("X");
|
||||||
|
assertEquals(1, s.size());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingSingleLatinCodePointShouldMoveIndex() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("X");
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
s.consume();
|
||||||
|
assertEquals(1, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingPastSingleLatinCodePointShouldThrow() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("X");
|
||||||
|
s.consume();
|
||||||
|
thrown.expect(IllegalStateException.class);
|
||||||
|
thrown.expectMessage("cannot consume EOF");
|
||||||
|
s.consume();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleLatinCodePointLookAheadShouldReturnCodePoint() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("X");
|
||||||
|
assertEquals('X', s.LA(1));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void multipleLatinCodePointsLookAheadShouldReturnCodePoints() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("XYZ");
|
||||||
|
assertEquals('X', s.LA(1));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals('Y', s.LA(2));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
assertEquals('Z', s.LA(3));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleLatinCodePointLookAheadPastEndShouldReturnEOF() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("X");
|
||||||
|
assertEquals(IntStream.EOF, s.LA(2));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleCJKCodePointHasSize1() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("\u611B");
|
||||||
|
assertEquals(1, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingSingleCJKCodePointShouldMoveIndex() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("\u611B");
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
s.consume();
|
||||||
|
assertEquals(1, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingPastSingleCJKCodePointShouldThrow() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("\u611B");
|
||||||
|
s.consume();
|
||||||
|
thrown.expect(IllegalStateException.class);
|
||||||
|
thrown.expectMessage("cannot consume EOF");
|
||||||
|
s.consume();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleCJKCodePointLookAheadShouldReturnCodePoint() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("\u611B");
|
||||||
|
assertEquals(0x611B, s.LA(1));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleCJKCodePointLookAheadPastEndShouldReturnEOF() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("\u611B");
|
||||||
|
assertEquals(IntStream.EOF, s.LA(2));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleEmojiCodePointHasSize1() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString());
|
||||||
|
assertEquals(1, s.size());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingSingleEmojiCodePointShouldMoveIndex() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
s.consume();
|
||||||
|
assertEquals(1, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void consumingPastEndOfEmojiCodePointWithShouldThrow() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString());
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
s.consume();
|
||||||
|
assertEquals(1, s.index());
|
||||||
|
thrown.expect(IllegalStateException.class);
|
||||||
|
thrown.expectMessage("cannot consume EOF");
|
||||||
|
s.consume();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleEmojiCodePointLookAheadShouldReturnCodePoint() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString());
|
||||||
|
assertEquals(0x1F4A9, s.LA(1));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void singleEmojiCodePointLookAheadPastEndShouldReturnEOF() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString());
|
||||||
|
assertEquals(IntStream.EOF, s.LA(2));
|
||||||
|
assertEquals(0, s.index());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTextWithLatin() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("0123456789");
|
||||||
|
assertEquals("34567", s.getText(Interval.of(3, 7)));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTextWithCJK() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("01234\u40946789");
|
||||||
|
assertEquals("34\u409467", s.getText(Interval.of(3, 7)));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTextWithEmoji() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder("01234")
|
||||||
|
.appendCodePoint(0x1F522)
|
||||||
|
.append("6789")
|
||||||
|
.toString());
|
||||||
|
assertEquals("34\uD83D\uDD2267", s.getText(Interval.of(3, 7)));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void toStringWithLatin() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("0123456789");
|
||||||
|
assertEquals("0123456789", s.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void toStringWithCJK() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("01234\u40946789");
|
||||||
|
assertEquals("01234\u40946789", s.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void toStringWithEmoji() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder("01234")
|
||||||
|
.appendCodePoint(0x1F522)
|
||||||
|
.append("6789")
|
||||||
|
.toString());
|
||||||
|
assertEquals("01234\uD83D\uDD226789", s.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookAheadWithLatin() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("0123456789");
|
||||||
|
assertEquals('5', s.LA(6));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookAheadWithCJK() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("01234\u40946789");
|
||||||
|
assertEquals(0x4094, s.LA(6));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookAheadWithEmoji() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder("01234")
|
||||||
|
.appendCodePoint(0x1F522)
|
||||||
|
.append("6789")
|
||||||
|
.toString());
|
||||||
|
assertEquals(0x1F522, s.LA(6));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void seekWithLatin() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("0123456789");
|
||||||
|
s.seek(5);
|
||||||
|
assertEquals('5', s.LA(1));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void seekWithCJK() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("01234\u40946789");
|
||||||
|
s.seek(5);
|
||||||
|
assertEquals(0x4094, s.LA(1));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void seekWithEmoji() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder("01234")
|
||||||
|
.appendCodePoint(0x1F522)
|
||||||
|
.append("6789")
|
||||||
|
.toString());
|
||||||
|
s.seek(5);
|
||||||
|
assertEquals(0x1F522, s.LA(1));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookBehindWithLatin() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("0123456789");
|
||||||
|
s.seek(6);
|
||||||
|
assertEquals('5', s.LA(-1));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookBehindWithCJK() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString("01234\u40946789");
|
||||||
|
s.seek(6);
|
||||||
|
assertEquals(0x4094, s.LA(-1));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void lookBehindWithEmoji() {
|
||||||
|
CodePointCharStream s = CharStreams.createWithString(
|
||||||
|
new StringBuilder("01234")
|
||||||
|
.appendCodePoint(0x1F522)
|
||||||
|
.append("6789")
|
||||||
|
.toString());
|
||||||
|
s.seek(6);
|
||||||
|
assertEquals(0x1F522, s.LA(-1));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,70 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime.java;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.misc.IntegerList;
|
||||||
|
import org.junit.Rule;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
||||||
|
public class TestIntegerList {
|
||||||
|
@Rule
|
||||||
|
public ExpectedException thrown = ExpectedException.none();
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void emptyListToEmptyCharArray() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
assertArrayEquals(new char[0], l.toCharArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void negativeIntegerToCharArrayThrows() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
l.add(-42);
|
||||||
|
thrown.expect(IllegalArgumentException.class);
|
||||||
|
l.toCharArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void surrogateRangeIntegerToCharArray() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
// Java allows dangling surrogates, so (currently) we do
|
||||||
|
// as well. We could change this if desired.
|
||||||
|
l.add(0xDC00);
|
||||||
|
char expected[] = new char[] { 0xDC00 };
|
||||||
|
assertArrayEquals(expected, l.toCharArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void tooLargeIntegerToCharArrayThrows() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
l.add(0x110000);
|
||||||
|
thrown.expect(IllegalArgumentException.class);
|
||||||
|
l.toCharArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unicodeBMPIntegerListToCharArray() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
l.add(0x35);
|
||||||
|
l.add(0x4E94);
|
||||||
|
l.add(0xFF15);
|
||||||
|
char expected[] = new char[] { 0x35, 0x4E94, 0xFF15 };
|
||||||
|
assertArrayEquals(expected, l.toCharArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unicodeSMPIntegerListToCharArray() {
|
||||||
|
IntegerList l = new IntegerList();
|
||||||
|
l.add(0x104A5);
|
||||||
|
l.add(0x116C5);
|
||||||
|
l.add(0x1D7FB);
|
||||||
|
char expected[] = new char[] { 0xD801, 0xDCA5, 0xD805, 0xDEC5, 0xD835, 0xDFFB };
|
||||||
|
assertArrayEquals(expected, l.toCharArray());
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,162 @@
|
||||||
|
/*
|
||||||
|
* 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.v4.test.runtime.java;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
import java.nio.IntBuffer;
|
||||||
|
|
||||||
|
import java.nio.charset.CharacterCodingException;
|
||||||
|
import java.nio.charset.CodingErrorAction;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.UTF8CodePointDecoder;
|
||||||
|
import org.junit.Rule;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
||||||
|
public class TestUTF8CodePointDecoder {
|
||||||
|
@Rule
|
||||||
|
public ExpectedException thrown = ExpectedException.none();
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodeEmptyByteBufferWritesNothing() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.allocate(0);
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(0);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(
|
||||||
|
utf8BytesIn,
|
||||||
|
codePointsOut,
|
||||||
|
true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(0, result.remaining());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodeLatinByteBufferWritesCodePoint() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = StandardCharsets.UTF_8.encode("X");
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(
|
||||||
|
utf8BytesIn,
|
||||||
|
codePointsOut,
|
||||||
|
true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals('X', result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodeCyrillicByteBufferWritesCodePoint() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = StandardCharsets.UTF_8.encode("\u042F");
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(
|
||||||
|
utf8BytesIn,
|
||||||
|
codePointsOut,
|
||||||
|
true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0x042F, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodeCJKByteBufferWritesCodePoint() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = StandardCharsets.UTF_8.encode("\u611B");
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(
|
||||||
|
utf8BytesIn,
|
||||||
|
codePointsOut,
|
||||||
|
true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0x611B, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodeEmojiByteBufferWritesCodePoint() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = StandardCharsets.UTF_8.encode(
|
||||||
|
new StringBuilder().appendCodePoint(0x1F4A9).toString()
|
||||||
|
);
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(
|
||||||
|
utf8BytesIn,
|
||||||
|
codePointsOut,
|
||||||
|
true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0x1F4A9, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingInvalidLeadInReplaceModeWritesSubstitutionCharacter() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xF8 });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0xFFFD, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingInvalidLeadInReportModeThrows() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPORT);
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xF8 });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
thrown.expect(CharacterCodingException.class);
|
||||||
|
thrown.expectMessage("Invalid UTF-8 leading byte 0xF8");
|
||||||
|
decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingInvalidTrailInReplaceModeWritesSubstitutionCharacter() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xC0, (byte)0xC0 });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0xFFFD, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingInvalidTrailInReportModeThrows() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPORT);
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xC0, (byte)0xC0 });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
thrown.expect(CharacterCodingException.class);
|
||||||
|
thrown.expectMessage("Invalid UTF-8 trailing byte 0xC0");
|
||||||
|
decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingNonShortestFormInReplaceModeWritesSubstitutionCharacter() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPLACE);
|
||||||
|
// 0xC1 0x9C would decode to \ (U+005C) if we didn't have this check
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xC1, (byte)0x9C });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
IntBuffer result = decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
result.flip();
|
||||||
|
assertEquals(1, result.remaining());
|
||||||
|
assertEquals(0xFFFD, result.get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void decodingNonShortestFormInReportModeThrows() throws Exception {
|
||||||
|
UTF8CodePointDecoder decoder = new UTF8CodePointDecoder(CodingErrorAction.REPORT);
|
||||||
|
// 0xC1 0x9C would decode to \ (U+005C) if we didn't have this check
|
||||||
|
ByteBuffer utf8BytesIn = ByteBuffer.wrap(new byte[] { (byte)0xC1, (byte)0x9C });
|
||||||
|
IntBuffer codePointsOut = IntBuffer.allocate(1);
|
||||||
|
thrown.expect(CharacterCodingException.class);
|
||||||
|
thrown.expectMessage("Code point 92 is out of expected range 128..2047");
|
||||||
|
decoder.decodeCodePointsFromBuffer(utf8BytesIn, codePointsOut, true);
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.java;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseJavaTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Java");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,3 +1,8 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2012-2016 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.v4.test.runtime.java.api;
|
package org.antlr.v4.test.runtime.java.api;
|
||||||
|
|
||||||
import org.antlr.v4.runtime.ParserRuleContext;
|
import org.antlr.v4.runtime.ParserRuleContext;
|
||||||
|
|
|
@ -0,0 +1,42 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2012-2016 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.v4.test.runtime.java.api;
|
||||||
|
|
||||||
|
import org.antlr.v4.runtime.ANTLRInputStream;
|
||||||
|
import org.antlr.v4.runtime.BufferedTokenStream;
|
||||||
|
import org.antlr.v4.runtime.CharStream;
|
||||||
|
import org.antlr.v4.runtime.Token;
|
||||||
|
import org.antlr.v4.runtime.TokenStream;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class contains tests for specific API functionality in {@link TokenStream} and derived types.
|
||||||
|
*/
|
||||||
|
public class TestTokenStream {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is a targeted regression test for antlr/antlr4#1584 ({@link BufferedTokenStream} cannot be reused after EOF).
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testBufferedTokenStreamReuseAfterFill() {
|
||||||
|
CharStream firstInput = new ANTLRInputStream("A");
|
||||||
|
BufferedTokenStream tokenStream = new BufferedTokenStream(new VisitorBasicLexer(firstInput));
|
||||||
|
tokenStream.fill();
|
||||||
|
Assert.assertEquals(2, tokenStream.size());
|
||||||
|
Assert.assertEquals(VisitorBasicLexer.A, tokenStream.get(0).getType());
|
||||||
|
Assert.assertEquals(Token.EOF, tokenStream.get(1).getType());
|
||||||
|
|
||||||
|
CharStream secondInput = new ANTLRInputStream("AA");
|
||||||
|
tokenStream.setTokenSource(new VisitorBasicLexer(secondInput));
|
||||||
|
tokenStream.fill();
|
||||||
|
Assert.assertEquals(3, tokenStream.size());
|
||||||
|
Assert.assertEquals(VisitorBasicLexer.A, tokenStream.get(0).getType());
|
||||||
|
Assert.assertEquals(VisitorBasicLexer.A, tokenStream.get(1).getType());
|
||||||
|
Assert.assertEquals(Token.EOF, tokenStream.get(2).getType());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,237 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2012-2016 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.v4.test.runtime.java.api;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import org.antlr.v4.runtime.ANTLRInputStream;
|
||||||
|
import org.antlr.v4.runtime.BaseErrorListener;
|
||||||
|
import org.antlr.v4.runtime.CommonTokenStream;
|
||||||
|
import org.antlr.v4.runtime.RecognitionException;
|
||||||
|
import org.antlr.v4.runtime.Recognizer;
|
||||||
|
import org.antlr.v4.runtime.tree.AbstractParseTreeVisitor;
|
||||||
|
import org.antlr.v4.runtime.tree.ErrorNode;
|
||||||
|
import org.antlr.v4.runtime.tree.RuleNode;
|
||||||
|
import org.antlr.v4.runtime.tree.TerminalNode;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
public class TestVisitors {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test verifies the basic behavior of visitors, with an emphasis on
|
||||||
|
* {@link AbstractParseTreeVisitor#visitTerminal}.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testVisitTerminalNode() {
|
||||||
|
String input = "A";
|
||||||
|
VisitorBasicLexer lexer = new VisitorBasicLexer(new ANTLRInputStream(input));
|
||||||
|
VisitorBasicParser parser = new VisitorBasicParser(new CommonTokenStream(lexer));
|
||||||
|
|
||||||
|
VisitorBasicParser.SContext context = parser.s();
|
||||||
|
Assert.assertEquals("(s A <EOF>)", context.toStringTree(parser));
|
||||||
|
|
||||||
|
VisitorBasicVisitor<String> listener = new VisitorBasicBaseVisitor<String>() {
|
||||||
|
@Override
|
||||||
|
public String visitTerminal(TerminalNode node) {
|
||||||
|
return node.getSymbol().toString() + "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String defaultResult() {
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String aggregateResult(String aggregate, String nextResult) {
|
||||||
|
return aggregate + nextResult;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
String result = listener.visit(context);
|
||||||
|
String expected =
|
||||||
|
"[@0,0:0='A',<1>,1:0]\n" +
|
||||||
|
"[@1,1:0='<EOF>',<-1>,1:1]\n";
|
||||||
|
Assert.assertEquals(expected, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test verifies the basic behavior of visitors, with an emphasis on
|
||||||
|
* {@link AbstractParseTreeVisitor#visitErrorNode}.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testVisitErrorNode() {
|
||||||
|
String input = "";
|
||||||
|
VisitorBasicLexer lexer = new VisitorBasicLexer(new ANTLRInputStream(input));
|
||||||
|
VisitorBasicParser parser = new VisitorBasicParser(new CommonTokenStream(lexer));
|
||||||
|
|
||||||
|
final List<String> errors = new ArrayList<>();
|
||||||
|
parser.removeErrorListeners();
|
||||||
|
parser.addErrorListener(new BaseErrorListener() {
|
||||||
|
@Override
|
||||||
|
public void syntaxError(Recognizer<?, ?> recognizer, Object offendingSymbol, int line, int charPositionInLine, String msg, RecognitionException e) {
|
||||||
|
errors.add("line " + line + ":" + charPositionInLine + " " + msg);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
VisitorBasicParser.SContext context = parser.s();
|
||||||
|
Assert.assertEquals("(s <missing 'A'> <EOF>)", context.toStringTree(parser));
|
||||||
|
Assert.assertEquals(1, errors.size());
|
||||||
|
Assert.assertEquals("line 1:0 missing 'A' at '<EOF>'", errors.get(0));
|
||||||
|
|
||||||
|
VisitorBasicVisitor<String> listener = new VisitorBasicBaseVisitor<String>() {
|
||||||
|
@Override
|
||||||
|
public String visitErrorNode(ErrorNode node) {
|
||||||
|
return "Error encountered: " + node.getSymbol();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String defaultResult() {
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String aggregateResult(String aggregate, String nextResult) {
|
||||||
|
return aggregate + nextResult;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
String result = listener.visit(context);
|
||||||
|
String expected = "Error encountered: [@-1,-1:-1='<missing 'A'>',<1>,1:0]";
|
||||||
|
Assert.assertEquals(expected, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test verifies that {@link AbstractParseTreeVisitor#visitChildren} does not call
|
||||||
|
* {@link ParseTreeVisitor#visit} after {@link AbstractParseTreeVisitor#shouldVisitNextChild} returns
|
||||||
|
* {@code false}.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testShouldNotVisitEOF() {
|
||||||
|
String input = "A";
|
||||||
|
VisitorBasicLexer lexer = new VisitorBasicLexer(new ANTLRInputStream(input));
|
||||||
|
VisitorBasicParser parser = new VisitorBasicParser(new CommonTokenStream(lexer));
|
||||||
|
|
||||||
|
VisitorBasicParser.SContext context = parser.s();
|
||||||
|
Assert.assertEquals("(s A <EOF>)", context.toStringTree(parser));
|
||||||
|
|
||||||
|
VisitorBasicVisitor<String> listener = new VisitorBasicBaseVisitor<String>() {
|
||||||
|
@Override
|
||||||
|
public String visitTerminal(TerminalNode node) {
|
||||||
|
return node.getSymbol().toString() + "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean shouldVisitNextChild(RuleNode node, String currentResult) {
|
||||||
|
return currentResult == null || currentResult.isEmpty();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
String result = listener.visit(context);
|
||||||
|
String expected = "[@0,0:0='A',<1>,1:0]\n";
|
||||||
|
Assert.assertEquals(expected, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test verifies that {@link AbstractParseTreeVisitor#shouldVisitNextChild} is called before visiting the first
|
||||||
|
* child. It also verifies that {@link AbstractParseTreeVisitor#defaultResult} provides the default return value for
|
||||||
|
* visiting a tree.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testShouldNotVisitTerminal() {
|
||||||
|
String input = "A";
|
||||||
|
VisitorBasicLexer lexer = new VisitorBasicLexer(new ANTLRInputStream(input));
|
||||||
|
VisitorBasicParser parser = new VisitorBasicParser(new CommonTokenStream(lexer));
|
||||||
|
|
||||||
|
VisitorBasicParser.SContext context = parser.s();
|
||||||
|
Assert.assertEquals("(s A <EOF>)", context.toStringTree(parser));
|
||||||
|
|
||||||
|
VisitorBasicVisitor<String> listener = new VisitorBasicBaseVisitor<String>() {
|
||||||
|
@Override
|
||||||
|
public String visitTerminal(TerminalNode node) {
|
||||||
|
throw new RuntimeException("Should not be reachable");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String defaultResult() {
|
||||||
|
return "default result";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean shouldVisitNextChild(RuleNode node, String currentResult) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
String result = listener.visit(context);
|
||||||
|
String expected = "default result";
|
||||||
|
Assert.assertEquals(expected, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test verifies that the visitor correctly dispatches calls for labeled outer alternatives.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testCalculatorVisitor() {
|
||||||
|
String input = "2 + 8 / 2";
|
||||||
|
VisitorCalcLexer lexer = new VisitorCalcLexer(new ANTLRInputStream(input));
|
||||||
|
VisitorCalcParser parser = new VisitorCalcParser(new CommonTokenStream(lexer));
|
||||||
|
|
||||||
|
VisitorCalcParser.SContext context = parser.s();
|
||||||
|
Assert.assertEquals("(s (expr (expr 2) + (expr (expr 8) / (expr 2))) <EOF>)", context.toStringTree(parser));
|
||||||
|
|
||||||
|
VisitorCalcVisitor<Integer> listener = new VisitorCalcBaseVisitor<Integer>() {
|
||||||
|
@Override
|
||||||
|
public Integer visitS(VisitorCalcParser.SContext ctx) {
|
||||||
|
return visit(ctx.expr());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Integer visitNumber(VisitorCalcParser.NumberContext ctx) {
|
||||||
|
return Integer.valueOf(ctx.INT().getText());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Integer visitMultiply(VisitorCalcParser.MultiplyContext ctx) {
|
||||||
|
Integer left = visit(ctx.expr(0));
|
||||||
|
Integer right = visit(ctx.expr(1));
|
||||||
|
if (ctx.MUL() != null) {
|
||||||
|
return left * right;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return left / right;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Integer visitAdd(VisitorCalcParser.AddContext ctx) {
|
||||||
|
Integer left = visit(ctx.expr(0));
|
||||||
|
Integer right = visit(ctx.expr(1));
|
||||||
|
if (ctx.ADD() != null) {
|
||||||
|
return left + right;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return left - right;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Integer defaultResult() {
|
||||||
|
throw new RuntimeException("Should not be reachable");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Integer aggregateResult(Integer aggregate, Integer nextResult) {
|
||||||
|
throw new RuntimeException("Should not be reachable");
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
int result = listener.visit(context);
|
||||||
|
int expected = 6;
|
||||||
|
Assert.assertEquals(expected, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,7 @@
|
||||||
|
grammar VisitorBasic;
|
||||||
|
|
||||||
|
s
|
||||||
|
: 'A' EOF
|
||||||
|
;
|
||||||
|
|
||||||
|
A : 'A';
|
|
@ -0,0 +1,18 @@
|
||||||
|
grammar VisitorCalc;
|
||||||
|
|
||||||
|
s
|
||||||
|
: expr EOF
|
||||||
|
;
|
||||||
|
|
||||||
|
expr
|
||||||
|
: INT # number
|
||||||
|
| expr (MUL | DIV) expr # multiply
|
||||||
|
| expr (ADD | SUB) expr # add
|
||||||
|
;
|
||||||
|
|
||||||
|
INT : [0-9]+;
|
||||||
|
MUL : '*';
|
||||||
|
DIV : '/';
|
||||||
|
ADD : '+';
|
||||||
|
SUB : '-';
|
||||||
|
WS : [ \t]+ -> channel(HIDDEN);
|
|
@ -53,13 +53,8 @@ import org.stringtemplate.v4.ST;
|
||||||
import org.stringtemplate.v4.STGroup;
|
import org.stringtemplate.v4.STGroup;
|
||||||
import org.stringtemplate.v4.STGroupString;
|
import org.stringtemplate.v4.STGroupString;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileWriter;
|
import java.io.FileWriter;
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.net.BindException;
|
import java.net.BindException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
@ -72,6 +67,7 @@ import java.util.Set;
|
||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
@ -528,41 +524,6 @@ public abstract class BaseBrowserTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader( new InputStreamReader(in) );
|
|
||||||
}
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line!=null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage)
|
GrammarSemanticsMessage expectedMessage)
|
||||||
throws Exception
|
throws Exception
|
||||||
|
@ -646,21 +607,6 @@ public abstract class BaseBrowserTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(String dir) {
|
protected void mkdir(String dir) {
|
||||||
File f = new File(dir);
|
File f = new File(dir);
|
||||||
f.mkdirs();
|
f.mkdirs();
|
||||||
|
@ -732,7 +678,7 @@ public abstract class BaseBrowserTest implements RuntimeTestSupport {
|
||||||
" test = function() {\r\n" +
|
" test = function() {\r\n" +
|
||||||
" document.getElementById('output').value = ''\r\n" +
|
" document.getElementById('output').value = ''\r\n" +
|
||||||
" var input = document.getElementById('input').value;\r\n" +
|
" var input = document.getElementById('input').value;\r\n" +
|
||||||
" var stream = new antlr4.InputStream(input);\n" +
|
" var stream = new antlr4.InputStream(input, true);\n" +
|
||||||
" var lexer = new " + lexerName + "." + lexerName + "(stream);\n" +
|
" var lexer = new " + lexerName + "." + lexerName + "(stream);\n" +
|
||||||
" lexer._listeners = [new listener()];\r\n" +
|
" lexer._listeners = [new listener()];\r\n" +
|
||||||
" var tokens = new antlr4.CommonTokenStream(lexer);\n" +
|
" var tokens = new antlr4.CommonTokenStream(lexer);\n" +
|
||||||
|
@ -791,7 +737,7 @@ public abstract class BaseBrowserTest implements RuntimeTestSupport {
|
||||||
" test = function() {\r\n" +
|
" test = function() {\r\n" +
|
||||||
" document.getElementById('output').value = ''\r\n" +
|
" document.getElementById('output').value = ''\r\n" +
|
||||||
" var input = document.getElementById('input').value;\r\n" +
|
" var input = document.getElementById('input').value;\r\n" +
|
||||||
" var chars = new antlr4.InputStream(input);\r\n" +
|
" var chars = new antlr4.InputStream(input, true);\r\n" +
|
||||||
" var lexer = new " + lexerName + "." + lexerName + "(chars);\r\n" +
|
" var lexer = new " + lexerName + "." + lexerName + "(chars);\r\n" +
|
||||||
" lexer._listeners = [new listener()];\r\n" +
|
" lexer._listeners = [new listener()];\r\n" +
|
||||||
" var stream = new antlr4.CommonTokenStream(lexer);\r\n" +
|
" var stream = new antlr4.CommonTokenStream(lexer);\r\n" +
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.javascript.chrome;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseChromeTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Chrome");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.javascript.explorer;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseExplorerTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Explorer");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.javascript.firefox;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseFirefoxTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Firefox");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -33,6 +33,7 @@ import org.antlr.v4.runtime.misc.Interval;
|
||||||
import org.antlr.v4.semantics.SemanticPipeline;
|
import org.antlr.v4.semantics.SemanticPipeline;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.DOTGenerator;
|
import org.antlr.v4.tool.DOTGenerator;
|
||||||
import org.antlr.v4.tool.Grammar;
|
import org.antlr.v4.tool.Grammar;
|
||||||
|
@ -43,15 +44,8 @@ import org.stringtemplate.v4.ST;
|
||||||
import org.stringtemplate.v4.STGroup;
|
import org.stringtemplate.v4.STGroup;
|
||||||
import org.stringtemplate.v4.STGroupString;
|
import org.stringtemplate.v4.STGroupString;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileOutputStream;
|
|
||||||
import java.io.FileWriter;
|
import java.io.FileWriter;
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
@ -64,6 +58,7 @@ import java.util.Set;
|
||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
@ -524,45 +519,6 @@ public class BaseNodeTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader(new InputStreamReader(in));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line != null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage) throws Exception {
|
GrammarSemanticsMessage expectedMessage) throws Exception {
|
||||||
ANTLRMessage foundMsg = null;
|
ANTLRMessage foundMsg = null;
|
||||||
|
@ -653,35 +609,6 @@ public class BaseNodeTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, InputStream content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
OutputStream output = new FileOutputStream(f);
|
|
||||||
while(content.available()>0) {
|
|
||||||
int b = content.read();
|
|
||||||
output.write(b);
|
|
||||||
}
|
|
||||||
output.close();
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(String dir) {
|
protected void mkdir(String dir) {
|
||||||
File f = new File(dir);
|
File f = new File(dir);
|
||||||
f.mkdirs();
|
f.mkdirs();
|
||||||
|
@ -716,7 +643,7 @@ public class BaseNodeTest implements RuntimeTestSupport {
|
||||||
+ "};\n"
|
+ "};\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "function main(argv) {\n"
|
+ "function main(argv) {\n"
|
||||||
+ " var input = new antlr4.FileStream(argv[2]);\n"
|
+ " var input = new antlr4.FileStream(argv[2], true);\n"
|
||||||
+ " var lexer = new <lexerName>.<lexerName>(input);\n"
|
+ " var lexer = new <lexerName>.<lexerName>(input);\n"
|
||||||
+ " var stream = new antlr4.CommonTokenStream(lexer);\n"
|
+ " var stream = new antlr4.CommonTokenStream(lexer);\n"
|
||||||
+ "<createParser>"
|
+ "<createParser>"
|
||||||
|
@ -752,7 +679,7 @@ public class BaseNodeTest implements RuntimeTestSupport {
|
||||||
+ "var <lexerName> = require('./<lexerName>');\n"
|
+ "var <lexerName> = require('./<lexerName>');\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "function main(argv) {\n"
|
+ "function main(argv) {\n"
|
||||||
+ " var input = new antlr4.FileStream(argv[2]);\n"
|
+ " var input = new antlr4.FileStream(argv[2], true);\n"
|
||||||
+ " var lexer = new <lexerName>.<lexerName>(input);\n"
|
+ " var lexer = new <lexerName>.<lexerName>(input);\n"
|
||||||
+ " var stream = new antlr4.CommonTokenStream(lexer);\n"
|
+ " var stream = new antlr4.CommonTokenStream(lexer);\n"
|
||||||
+ " stream.fill();\n"
|
+ " stream.fill();\n"
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.javascript.node;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseNodeTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Node");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.javascript.safari;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseSafariTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Safari");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -36,6 +36,8 @@ import org.antlr.v4.runtime.tree.ParseTree;
|
||||||
import org.antlr.v4.semantics.SemanticPipeline;
|
import org.antlr.v4.semantics.SemanticPipeline;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
|
import org.antlr.v4.test.runtime.TestOutputReading;
|
||||||
import org.antlr.v4.tool.ANTLRMessage;
|
import org.antlr.v4.tool.ANTLRMessage;
|
||||||
import org.antlr.v4.tool.DOTGenerator;
|
import org.antlr.v4.tool.DOTGenerator;
|
||||||
import org.antlr.v4.tool.Grammar;
|
import org.antlr.v4.tool.Grammar;
|
||||||
|
@ -49,13 +51,8 @@ import org.stringtemplate.v4.ST;
|
||||||
import org.stringtemplate.v4.STGroup;
|
import org.stringtemplate.v4.STGroup;
|
||||||
import org.stringtemplate.v4.STGroupString;
|
import org.stringtemplate.v4.STGroupString;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileWriter;
|
import java.nio.file.Path;
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.lang.reflect.InvocationTargetException;
|
import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
|
@ -70,6 +67,7 @@ import java.util.Set;
|
||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertArrayEquals;
|
import static org.junit.Assert.assertArrayEquals;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
@ -488,24 +486,21 @@ public abstract class BasePythonTest implements RuntimeTestSupport {
|
||||||
public String execModule(String fileName) {
|
public String execModule(String fileName) {
|
||||||
String pythonPath = locatePython();
|
String pythonPath = locatePython();
|
||||||
String runtimePath = locateRuntime();
|
String runtimePath = locateRuntime();
|
||||||
String modulePath = new File(new File(tmpdir), fileName).getAbsolutePath();
|
File tmpdirFile = new File(tmpdir);
|
||||||
String inputPath = new File(new File(tmpdir), "input").getAbsolutePath();
|
String modulePath = new File(tmpdirFile, fileName).getAbsolutePath();
|
||||||
|
String inputPath = new File(tmpdirFile, "input").getAbsolutePath();
|
||||||
|
Path outputPath = tmpdirFile.toPath().resolve("output").toAbsolutePath();
|
||||||
try {
|
try {
|
||||||
ProcessBuilder builder = new ProcessBuilder( pythonPath, modulePath, inputPath );
|
ProcessBuilder builder = new ProcessBuilder( pythonPath, modulePath, inputPath, outputPath.toString() );
|
||||||
builder.environment().put("PYTHONPATH",runtimePath);
|
builder.environment().put("PYTHONPATH",runtimePath);
|
||||||
builder.directory(new File(tmpdir));
|
builder.environment().put("PYTHONIOENCODING", "utf-8");
|
||||||
|
builder.directory(tmpdirFile);
|
||||||
Process process = builder.start();
|
Process process = builder.start();
|
||||||
StreamVacuum stdoutVacuum = new StreamVacuum(process.getInputStream());
|
|
||||||
StreamVacuum stderrVacuum = new StreamVacuum(process.getErrorStream());
|
StreamVacuum stderrVacuum = new StreamVacuum(process.getErrorStream());
|
||||||
stdoutVacuum.start();
|
|
||||||
stderrVacuum.start();
|
stderrVacuum.start();
|
||||||
process.waitFor();
|
process.waitFor();
|
||||||
stdoutVacuum.join();
|
|
||||||
stderrVacuum.join();
|
stderrVacuum.join();
|
||||||
String output = stdoutVacuum.toString();
|
String output = TestOutputReading.read(outputPath);
|
||||||
if ( output.length()==0 ) {
|
|
||||||
output = null;
|
|
||||||
}
|
|
||||||
if ( stderrVacuum.toString().length()>0 ) {
|
if ( stderrVacuum.toString().length()>0 ) {
|
||||||
this.stderrDuringParse = stderrVacuum.toString();
|
this.stderrDuringParse = stderrVacuum.toString();
|
||||||
}
|
}
|
||||||
|
@ -651,41 +646,6 @@ public abstract class BasePythonTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader( new InputStreamReader(in) );
|
|
||||||
}
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line!=null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/** wait for the thread to finish */
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
protected void checkGrammarSemanticsError(ErrorQueue equeue,
|
||||||
GrammarSemanticsMessage expectedMessage)
|
GrammarSemanticsMessage expectedMessage)
|
||||||
throws Exception
|
throws Exception
|
||||||
|
@ -769,21 +729,6 @@ public abstract class BasePythonTest implements RuntimeTestSupport {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void mkdir(String dir) {
|
protected void mkdir(String dir) {
|
||||||
File f = new File(dir);
|
File f = new File(dir);
|
||||||
f.mkdirs();
|
f.mkdirs();
|
||||||
|
|
|
@ -9,6 +9,8 @@ package org.antlr.v4.test.runtime.python2;
|
||||||
import org.antlr.v4.test.runtime.python.BasePythonTest;
|
import org.antlr.v4.test.runtime.python.BasePythonTest;
|
||||||
import org.stringtemplate.v4.ST;
|
import org.stringtemplate.v4.ST;
|
||||||
|
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
|
|
||||||
public class BasePython2Test extends BasePythonTest {
|
public class BasePython2Test extends BasePythonTest {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -26,16 +28,18 @@ public class BasePython2Test extends BasePythonTest {
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
"from __future__ import print_function\n"
|
"from __future__ import print_function\n"
|
||||||
+ "import sys\n"
|
+ "import sys\n"
|
||||||
|
+ "import codecs\n"
|
||||||
+ "from antlr4 import *\n"
|
+ "from antlr4 import *\n"
|
||||||
+ "from <lexerName> import <lexerName>\n"
|
+ "from <lexerName> import <lexerName>\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "def main(argv):\n"
|
+ "def main(argv):\n"
|
||||||
+ " input = FileStream(argv[1])\n"
|
+ " input = FileStream(argv[1], encoding='utf-8', errors='replace')\n"
|
||||||
+ " lexer = <lexerName>(input)\n"
|
+ " with codecs.open(argv[2], 'w', 'utf-8', 'replace') as output:\n"
|
||||||
+ " stream = CommonTokenStream(lexer)\n"
|
+ " lexer = <lexerName>(input, output)\n"
|
||||||
+ " stream.fill()\n"
|
+ " stream = CommonTokenStream(lexer)\n"
|
||||||
+ " [ print(str(t)) for t in stream.tokens ]\n"
|
+ " stream.fill()\n"
|
||||||
+ (showDFA ? " print(lexer._interp.decisionToDFA[Lexer.DEFAULT_MODE].toLexerString(), end='')\n"
|
+ " [ print(t, file=output) for t in stream.tokens ]\n"
|
||||||
|
+ (showDFA ? " print(lexer._interp.decisionToDFA[Lexer.DEFAULT_MODE].toLexerString(), end='', file=output)\n"
|
||||||
: "") + "\n" + "if __name__ == '__main__':\n"
|
: "") + "\n" + "if __name__ == '__main__':\n"
|
||||||
+ " main(sys.argv)\n" + "\n");
|
+ " main(sys.argv)\n" + "\n");
|
||||||
outputFileST.add("lexerName", lexerName);
|
outputFileST.add("lexerName", lexerName);
|
||||||
|
@ -50,6 +54,7 @@ public class BasePython2Test extends BasePythonTest {
|
||||||
parserStartRuleName += "()";
|
parserStartRuleName += "()";
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
"import sys\n"
|
"import sys\n"
|
||||||
|
+ "import codecs\n"
|
||||||
+ "from antlr4 import *\n"
|
+ "from antlr4 import *\n"
|
||||||
+ "from <lexerName> import <lexerName>\n"
|
+ "from <lexerName> import <lexerName>\n"
|
||||||
+ "from <parserName> import <parserName>\n"
|
+ "from <parserName> import <parserName>\n"
|
||||||
|
@ -74,20 +79,21 @@ public class BasePython2Test extends BasePythonTest {
|
||||||
+ " raise IllegalStateException(\"Invalid parse tree shape detected.\")\n"
|
+ " raise IllegalStateException(\"Invalid parse tree shape detected.\")\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "def main(argv):\n"
|
+ "def main(argv):\n"
|
||||||
+ " input = FileStream(argv[1])\n"
|
+ " input = FileStream(argv[1], encoding='utf-8', errors='replace')\n"
|
||||||
+ " lexer = <lexerName>(input)\n"
|
+ " with codecs.open(argv[2], 'w', 'utf-8', 'replace') as output:\n"
|
||||||
+ " stream = CommonTokenStream(lexer)\n"
|
+ " lexer = <lexerName>(input, output)\n"
|
||||||
|
+ " stream = CommonTokenStream(lexer)\n"
|
||||||
+ "<createParser>"
|
+ "<createParser>"
|
||||||
+ " parser.buildParseTrees = True\n"
|
+ " parser.buildParseTrees = True\n"
|
||||||
+ " tree = parser.<parserStartRuleName>\n"
|
+ " tree = parser.<parserStartRuleName>\n"
|
||||||
+ " ParseTreeWalker.DEFAULT.walk(TreeShapeListener(), tree)\n"
|
+ " ParseTreeWalker.DEFAULT.walk(TreeShapeListener(), tree)\n"
|
||||||
+ "\n" + "if __name__ == '__main__':\n"
|
+ "\n" + "if __name__ == '__main__':\n"
|
||||||
+ " main(sys.argv)\n" + "\n");
|
+ " main(sys.argv)\n" + "\n");
|
||||||
String stSource = " parser = <parserName>(stream)\n";
|
String stSource = " parser = <parserName>(stream, output)\n";
|
||||||
if(debug)
|
if(debug)
|
||||||
stSource += " parser.addErrorListener(DiagnosticErrorListener())\n";
|
stSource += " parser.addErrorListener(DiagnosticErrorListener())\n";
|
||||||
if(trace)
|
if(trace)
|
||||||
stSource += " parser.setTrace(True)\n";
|
stSource += " parser.setTrace(True)\n";
|
||||||
ST createParserST = new ST(stSource);
|
ST createParserST = new ST(stSource);
|
||||||
outputFileST.add("createParser", createParserST);
|
outputFileST.add("createParser", createParserST);
|
||||||
outputFileST.add("parserName", parserName);
|
outputFileST.add("parserName", parserName);
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.python2;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BasePython2Test());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Python2");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -8,6 +8,8 @@ package org.antlr.v4.test.runtime.python3;
|
||||||
import org.antlr.v4.test.runtime.python.BasePythonTest;
|
import org.antlr.v4.test.runtime.python.BasePythonTest;
|
||||||
import org.stringtemplate.v4.ST;
|
import org.stringtemplate.v4.ST;
|
||||||
|
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
|
|
||||||
public class BasePython3Test extends BasePythonTest {
|
public class BasePython3Test extends BasePythonTest {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -24,16 +26,18 @@ public class BasePython3Test extends BasePythonTest {
|
||||||
protected void writeLexerTestFile(String lexerName, boolean showDFA) {
|
protected void writeLexerTestFile(String lexerName, boolean showDFA) {
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
"import sys\n"
|
"import sys\n"
|
||||||
|
+ "import codecs\n"
|
||||||
+ "from antlr4 import *\n"
|
+ "from antlr4 import *\n"
|
||||||
+ "from <lexerName> import <lexerName>\n"
|
+ "from <lexerName> import <lexerName>\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "def main(argv):\n"
|
+ "def main(argv):\n"
|
||||||
+ " input = FileStream(argv[1])\n"
|
+ " input = FileStream(argv[1], encoding='utf-8', errors='replace')\n"
|
||||||
+ " lexer = <lexerName>(input)\n"
|
+ " with codecs.open(argv[2], 'w', 'utf-8', 'replace') as output:\n"
|
||||||
+ " stream = CommonTokenStream(lexer)\n"
|
+ " lexer = <lexerName>(input, output)\n"
|
||||||
+ " stream.fill()\n"
|
+ " stream = CommonTokenStream(lexer)\n"
|
||||||
+ " [ print(str(t)) for t in stream.tokens ]\n"
|
+ " stream.fill()\n"
|
||||||
+ (showDFA ? " print(lexer._interp.decisionToDFA[Lexer.DEFAULT_MODE].toLexerString(), end='')\n"
|
+ " [ print(t, file=output) for t in stream.tokens ]\n"
|
||||||
|
+ (showDFA ? " print(lexer._interp.decisionToDFA[Lexer.DEFAULT_MODE].toLexerString(), end='', file=output)\n"
|
||||||
: "") + "\n" + "if __name__ == '__main__':\n"
|
: "") + "\n" + "if __name__ == '__main__':\n"
|
||||||
+ " main(sys.argv)\n" + "\n");
|
+ " main(sys.argv)\n" + "\n");
|
||||||
outputFileST.add("lexerName", lexerName);
|
outputFileST.add("lexerName", lexerName);
|
||||||
|
@ -48,6 +52,7 @@ public class BasePython3Test extends BasePythonTest {
|
||||||
parserStartRuleName += "()";
|
parserStartRuleName += "()";
|
||||||
ST outputFileST = new ST(
|
ST outputFileST = new ST(
|
||||||
"import sys\n"
|
"import sys\n"
|
||||||
|
+ "import codecs\n"
|
||||||
+ "from antlr4 import *\n"
|
+ "from antlr4 import *\n"
|
||||||
+ "from <lexerName> import <lexerName>\n"
|
+ "from <lexerName> import <lexerName>\n"
|
||||||
+ "from <parserName> import <parserName>\n"
|
+ "from <parserName> import <parserName>\n"
|
||||||
|
@ -72,20 +77,21 @@ public class BasePython3Test extends BasePythonTest {
|
||||||
+ " raise IllegalStateException(\"Invalid parse tree shape detected.\")\n"
|
+ " raise IllegalStateException(\"Invalid parse tree shape detected.\")\n"
|
||||||
+ "\n"
|
+ "\n"
|
||||||
+ "def main(argv):\n"
|
+ "def main(argv):\n"
|
||||||
+ " input = FileStream(argv[1])\n"
|
+ " input = FileStream(argv[1], encoding='utf-8', errors='replace')\n"
|
||||||
+ " lexer = <lexerName>(input)\n"
|
+ " with codecs.open(argv[2], 'w', 'utf-8', 'replace') as output:\n"
|
||||||
+ " stream = CommonTokenStream(lexer)\n"
|
+ " lexer = <lexerName>(input, output)\n"
|
||||||
|
+ " stream = CommonTokenStream(lexer)\n"
|
||||||
+ "<createParser>"
|
+ "<createParser>"
|
||||||
+ " parser.buildParseTrees = True\n"
|
+ " parser.buildParseTrees = True\n"
|
||||||
+ " tree = parser.<parserStartRuleName>\n"
|
+ " tree = parser.<parserStartRuleName>\n"
|
||||||
+ " ParseTreeWalker.DEFAULT.walk(TreeShapeListener(), tree)\n"
|
+ " ParseTreeWalker.DEFAULT.walk(TreeShapeListener(), tree)\n"
|
||||||
+ "\n" + "if __name__ == '__main__':\n"
|
+ "\n" + "if __name__ == '__main__':\n"
|
||||||
+ " main(sys.argv)\n" + "\n");
|
+ " main(sys.argv)\n" + "\n");
|
||||||
String stSource = " parser = <parserName>(stream)\n";
|
String stSource = " parser = <parserName>(stream, output)\n";
|
||||||
if (debug)
|
if (debug)
|
||||||
stSource += " parser.addErrorListener(DiagnosticErrorListener())\n";
|
stSource += " parser.addErrorListener(DiagnosticErrorListener())\n";
|
||||||
if (trace)
|
if (trace)
|
||||||
stSource += " parser.setTrace(True)\n";
|
stSource += " parser.setTrace(True)\n";
|
||||||
ST createParserST = new ST(stSource);
|
ST createParserST = new ST(stSource);
|
||||||
outputFileST.add("createParser", createParserST);
|
outputFileST.add("createParser", createParserST);
|
||||||
outputFileST.add("parserName", parserName);
|
outputFileST.add("parserName", parserName);
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.python3;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BasePython3Test());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Python3");
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -9,15 +9,11 @@ package org.antlr.v4.test.runtime.swift;
|
||||||
import org.antlr.v4.Tool;
|
import org.antlr.v4.Tool;
|
||||||
import org.antlr.v4.test.runtime.ErrorQueue;
|
import org.antlr.v4.test.runtime.ErrorQueue;
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
import org.antlr.v4.test.runtime.RuntimeTestSupport;
|
||||||
|
import org.antlr.v4.test.runtime.StreamVacuum;
|
||||||
import org.stringtemplate.v4.ST;
|
import org.stringtemplate.v4.ST;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.BufferedWriter;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileWriter;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.InputStreamReader;
|
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
@ -27,6 +23,7 @@ import java.util.List;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.antlrOnString;
|
||||||
|
import static org.antlr.v4.test.runtime.BaseRuntimeTest.writeFile;
|
||||||
import static org.junit.Assert.assertTrue;
|
import static org.junit.Assert.assertTrue;
|
||||||
|
|
||||||
public class BaseSwiftTest implements RuntimeTestSupport {
|
public class BaseSwiftTest implements RuntimeTestSupport {
|
||||||
|
@ -57,7 +54,7 @@ public class BaseSwiftTest implements RuntimeTestSupport {
|
||||||
//add antlr.swift
|
//add antlr.swift
|
||||||
final ClassLoader loader = Thread.currentThread().getContextClassLoader();
|
final ClassLoader loader = Thread.currentThread().getContextClassLoader();
|
||||||
|
|
||||||
final URL swiftRuntime = loader.getResource("Swift/Antlr4");
|
final URL swiftRuntime = loader.getResource("Swift/Sources/Antlr4");
|
||||||
if (swiftRuntime == null) {
|
if (swiftRuntime == null) {
|
||||||
throw new RuntimeException("Swift runtime file not found at:" + swiftRuntime.getPath());
|
throw new RuntimeException("Swift runtime file not found at:" + swiftRuntime.getPath());
|
||||||
}
|
}
|
||||||
|
@ -118,49 +115,6 @@ public class BaseSwiftTest implements RuntimeTestSupport {
|
||||||
return runProcess(argsString, ANTLR_FRAMEWORK_DIR);
|
return runProcess(argsString, ANTLR_FRAMEWORK_DIR);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StreamVacuum implements Runnable {
|
|
||||||
StringBuilder buf = new StringBuilder();
|
|
||||||
BufferedReader in;
|
|
||||||
Thread sucker;
|
|
||||||
|
|
||||||
public StreamVacuum(InputStream in) {
|
|
||||||
this.in = new BufferedReader(new InputStreamReader(in));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void start() {
|
|
||||||
sucker = new Thread(this);
|
|
||||||
sucker.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
try {
|
|
||||||
String line = in.readLine();
|
|
||||||
while (line != null) {
|
|
||||||
buf.append(line);
|
|
||||||
buf.append('\n');
|
|
||||||
line = in.readLine();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException ioe) {
|
|
||||||
System.err.println("can't read output from process");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* wait for the thread to finish
|
|
||||||
*/
|
|
||||||
public void join() throws InterruptedException {
|
|
||||||
sucker.join();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return buf.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public String tmpdir = null;
|
public String tmpdir = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -364,20 +318,6 @@ public class BaseSwiftTest implements RuntimeTestSupport {
|
||||||
return execTest();
|
return execTest();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeFile(String dir, String fileName, String content) {
|
|
||||||
try {
|
|
||||||
File f = new File(dir, fileName);
|
|
||||||
FileWriter w = new FileWriter(f);
|
|
||||||
BufferedWriter bw = new BufferedWriter(w);
|
|
||||||
bw.write(content);
|
|
||||||
bw.close();
|
|
||||||
w.close();
|
|
||||||
} catch (IOException ioe) {
|
|
||||||
System.err.println("can't write file");
|
|
||||||
ioe.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void writeParserTestFile(String parserName,
|
protected void writeParserTestFile(String parserName,
|
||||||
String lexerName,
|
String lexerName,
|
||||||
String parserStartRuleName,
|
String parserStartRuleName,
|
||||||
|
|
|
@ -1,26 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2012-2016 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.v4.test.runtime.swift;
|
|
||||||
|
|
||||||
import org.antlr.v4.test.runtime.BaseRuntimeTest;
|
|
||||||
import org.antlr.v4.test.runtime.RuntimeTestDescriptor;
|
|
||||||
import org.antlr.v4.test.runtime.descriptors.VisitorsDescriptors;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.Parameterized;
|
|
||||||
|
|
||||||
@RunWith(Parameterized.class)
|
|
||||||
public class TestVisitors extends BaseRuntimeTest {
|
|
||||||
public TestVisitors(RuntimeTestDescriptor descriptor) {
|
|
||||||
super(descriptor,new BaseSwiftTest());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Parameterized.Parameters(name="{0}")
|
|
||||||
public static RuntimeTestDescriptor[] getAllTestDescriptors() {
|
|
||||||
return BaseRuntimeTest.getRuntimeTestDescriptors(VisitorsDescriptors.class, "Swift");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
|
@ -0,0 +1,21 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<Import Project="$(VSToolsPath)\DotNet\Microsoft.DotNet.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>12962409-846e-4b80-933a-bc484d264132</ProjectGuid>
|
||||||
|
<RootNamespace>Antlr4.Runtime.dotnet</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">.\obj</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">.\bin\</OutputPath>
|
||||||
|
<TargetFrameworkVersion>v4.5.2</TargetFrameworkVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DotNet\Microsoft.DotNet.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
|
@ -4,36 +4,19 @@
|
||||||
*/
|
*/
|
||||||
using System;
|
using System;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
using System.Text;
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Misc;
|
using Antlr4.Runtime.Misc;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
/// <summary>
|
public abstract class BaseInputCharStream : ICharStream
|
||||||
/// Vacuum all input from a
|
|
||||||
/// <see cref="System.IO.TextReader"/>
|
|
||||||
/// /
|
|
||||||
/// <see cref="System.IO.Stream"/>
|
|
||||||
/// and then treat it
|
|
||||||
/// like a
|
|
||||||
/// <c>char[]</c>
|
|
||||||
/// buffer. Can also pass in a
|
|
||||||
/// <see cref="string"/>
|
|
||||||
/// or
|
|
||||||
/// <c>char[]</c>
|
|
||||||
/// to use.
|
|
||||||
/// <p>If you need encoding, pass in stream/reader with correct encoding.</p>
|
|
||||||
/// </summary>
|
|
||||||
public class AntlrInputStream : ICharStream
|
|
||||||
{
|
{
|
||||||
public const int ReadBufferSize = 1024;
|
public const int ReadBufferSize = 1024;
|
||||||
|
|
||||||
public const int InitialBufferSize = 1024;
|
public const int InitialBufferSize = 1024;
|
||||||
|
|
||||||
/// <summary>The data being scanned</summary>
|
|
||||||
protected internal char[] data;
|
|
||||||
|
|
||||||
/// <summary>How many characters are actually in the buffer</summary>
|
/// <summary>How many characters are actually in the buffer</summary>
|
||||||
protected internal int n;
|
protected internal int n;
|
||||||
|
|
||||||
|
@ -43,72 +26,6 @@ namespace Antlr4.Runtime
|
||||||
/// <summary>What is name or source of this char stream?</summary>
|
/// <summary>What is name or source of this char stream?</summary>
|
||||||
public string name;
|
public string name;
|
||||||
|
|
||||||
public AntlrInputStream()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Copy data in string to a local char array</summary>
|
|
||||||
public AntlrInputStream(string input)
|
|
||||||
{
|
|
||||||
this.data = input.ToCharArray();
|
|
||||||
this.n = input.Length;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>This is the preferred constructor for strings as no data is copied</summary>
|
|
||||||
public AntlrInputStream(char[] data, int numberOfActualCharsInArray)
|
|
||||||
{
|
|
||||||
this.data = data;
|
|
||||||
this.n = numberOfActualCharsInArray;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(TextReader r)
|
|
||||||
: this(r, InitialBufferSize, ReadBufferSize)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(TextReader r, int initialSize)
|
|
||||||
: this(r, initialSize, ReadBufferSize)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(TextReader r, int initialSize, int readChunkSize)
|
|
||||||
{
|
|
||||||
Load(r, initialSize, readChunkSize);
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(Stream input)
|
|
||||||
: this(new StreamReader(input), InitialBufferSize)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(Stream input, int initialSize)
|
|
||||||
: this(new StreamReader(input), initialSize)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public AntlrInputStream(Stream input, int initialSize, int readChunkSize)
|
|
||||||
: this(new StreamReader(input), initialSize, readChunkSize)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <exception cref="System.IO.IOException"/>
|
|
||||||
public virtual void Load(TextReader r, int size, int readChunkSize)
|
|
||||||
{
|
|
||||||
if (r == null)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
data = r.ReadToEnd().ToCharArray();
|
|
||||||
n = data.Length;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Reset the stream so that it's in the same state it was
|
/// Reset the stream so that it's in the same state it was
|
||||||
/// when the object was created *except* the data array is not
|
/// when the object was created *except* the data array is not
|
||||||
|
@ -163,7 +80,7 @@ namespace Antlr4.Runtime
|
||||||
}
|
}
|
||||||
//System.out.println("char LA("+i+")="+(char)data[p+i-1]+"; p="+p);
|
//System.out.println("char LA("+i+")="+(char)data[p+i-1]+"; p="+p);
|
||||||
//System.out.println("LA("+i+"); p="+p+" n="+n+" data.length="+data.length);
|
//System.out.println("LA("+i+"); p="+p+" n="+n+" data.length="+data.length);
|
||||||
return data[p + i - 1];
|
return ValueAt(p + i - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual int Lt(int i)
|
public virtual int Lt(int i)
|
||||||
|
@ -243,10 +160,16 @@ namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
return string.Empty;
|
return string.Empty;
|
||||||
}
|
}
|
||||||
// System.err.println("data: "+Arrays.toString(data)+", n="+n+
|
return ConvertDataToString(start, count);
|
||||||
// ", start="+start+
|
}
|
||||||
// ", stop="+stop);
|
|
||||||
return new string(data, start, count);
|
protected abstract int ValueAt(int i);
|
||||||
|
|
||||||
|
protected abstract string ConvertDataToString(int start, int count);
|
||||||
|
|
||||||
|
public override sealed string ToString()
|
||||||
|
{
|
||||||
|
return ConvertDataToString(0, n);
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual string SourceName
|
public virtual string SourceName
|
||||||
|
@ -260,10 +183,148 @@ namespace Antlr4.Runtime
|
||||||
return name;
|
return name;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public override string ToString()
|
/// <summary>
|
||||||
|
/// Vacuum all input from a
|
||||||
|
/// <see cref="System.IO.TextReader"/>
|
||||||
|
/// /
|
||||||
|
/// <see cref="System.IO.Stream"/>
|
||||||
|
/// and then treat it
|
||||||
|
/// like a
|
||||||
|
/// <c>char[]</c>
|
||||||
|
/// buffer. Can also pass in a
|
||||||
|
/// <see cref="string"/>
|
||||||
|
/// or
|
||||||
|
/// <c>char[]</c>
|
||||||
|
/// to use.
|
||||||
|
/// <p>If you need encoding, pass in stream/reader with correct encoding.</p>
|
||||||
|
/// </summary>
|
||||||
|
public class AntlrInputStream : BaseInputCharStream
|
||||||
|
{
|
||||||
|
/// <summary>The data being scanned</summary>
|
||||||
|
protected internal char[] data;
|
||||||
|
|
||||||
|
public AntlrInputStream()
|
||||||
{
|
{
|
||||||
return new string(data);
|
}
|
||||||
|
|
||||||
|
/// <summary>Copy data in string to a local char array</summary>
|
||||||
|
public AntlrInputStream(string input)
|
||||||
|
{
|
||||||
|
this.data = input.ToCharArray();
|
||||||
|
this.n = input.Length;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>This is the preferred constructor for strings as no data is copied</summary>
|
||||||
|
public AntlrInputStream(char[] data, int numberOfActualCharsInArray)
|
||||||
|
{
|
||||||
|
this.data = data;
|
||||||
|
this.n = numberOfActualCharsInArray;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(TextReader r)
|
||||||
|
: this(r, InitialBufferSize, ReadBufferSize)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(TextReader r, int initialSize)
|
||||||
|
: this(r, initialSize, ReadBufferSize)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(TextReader r, int initialSize, int readChunkSize)
|
||||||
|
{
|
||||||
|
Load(r, initialSize, readChunkSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(Stream input)
|
||||||
|
: this(new StreamReader(input), InitialBufferSize)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(Stream input, int initialSize)
|
||||||
|
: this(new StreamReader(input), initialSize)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public AntlrInputStream(Stream input, int initialSize, int readChunkSize)
|
||||||
|
: this(new StreamReader(input), initialSize, readChunkSize)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <exception cref="System.IO.IOException"/>
|
||||||
|
public virtual void Load(TextReader r, int size, int readChunkSize)
|
||||||
|
{
|
||||||
|
if (r == null)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
data = r.ReadToEnd().ToCharArray();
|
||||||
|
n = data.Length;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override int ValueAt(int i)
|
||||||
|
{
|
||||||
|
return data[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override string ConvertDataToString(int start, int count)
|
||||||
|
{
|
||||||
|
// System.err.println("data: "+Arrays.toString(data)+", n="+n+
|
||||||
|
// ", start="+start+
|
||||||
|
// ", stop="+stop);
|
||||||
|
return new string(data, start, count);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Alternative to
|
||||||
|
/// <see cref="ANTLRInputStream"/>
|
||||||
|
/// which treats the input as a series of Unicode code points,
|
||||||
|
/// instead of a series of UTF-16 code units.
|
||||||
|
///
|
||||||
|
/// Use this if you need to parse input which potentially contains
|
||||||
|
/// Unicode values > U+FFFF.
|
||||||
|
/// </summary>
|
||||||
|
public class CodePointCharStream : BaseInputCharStream
|
||||||
|
{
|
||||||
|
private int[] data;
|
||||||
|
|
||||||
|
public CodePointCharStream(string input)
|
||||||
|
{
|
||||||
|
this.data = new int[input.Length];
|
||||||
|
int dataIdx = 0;
|
||||||
|
for (int i = 0; i < input.Length; ) {
|
||||||
|
var codePoint = Char.ConvertToUtf32(input, i);
|
||||||
|
data[dataIdx++] = codePoint;
|
||||||
|
if (dataIdx > data.Length) {
|
||||||
|
Array.Resize(ref data, data.Length * 2);
|
||||||
|
}
|
||||||
|
i += codePoint <= 0xFFFF ? 1 : 2;
|
||||||
|
}
|
||||||
|
this.n = dataIdx;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override int ValueAt(int i)
|
||||||
|
{
|
||||||
|
return data[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override string ConvertDataToString(int start, int count)
|
||||||
|
{
|
||||||
|
var sb = new StringBuilder(count);
|
||||||
|
for (int i = start; i < start + count; i++) {
|
||||||
|
sb.Append(Char.ConvertFromUtf32(data[i]));
|
||||||
|
}
|
||||||
|
return sb.ToString();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -380,7 +380,7 @@ namespace Antlr4.Runtime.Atn
|
||||||
|
|
||||||
protected ATNState GetReachableTarget(Transition trans, int t)
|
protected ATNState GetReachableTarget(Transition trans, int t)
|
||||||
{
|
{
|
||||||
if (trans.Matches(t, char.MinValue, char.MaxValue))
|
if (trans.Matches(t, Lexer.MinCharValue, Lexer.MaxCharValue))
|
||||||
{
|
{
|
||||||
return trans.target;
|
return trans.target;
|
||||||
}
|
}
|
||||||
|
@ -572,7 +572,7 @@ namespace Antlr4.Runtime.Atn
|
||||||
case TransitionType.SET:
|
case TransitionType.SET:
|
||||||
if (treatEofAsEpsilon)
|
if (treatEofAsEpsilon)
|
||||||
{
|
{
|
||||||
if (t.Matches(IntStreamConstants.EOF, char.MinValue, char.MaxValue))
|
if (t.Matches(IntStreamConstants.EOF, Lexer.MinCharValue, Lexer.MaxCharValue))
|
||||||
{
|
{
|
||||||
c = new LexerATNConfig(config, t.target);
|
c = new LexerATNConfig(config, t.target);
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -1,42 +0,0 @@
|
||||||
/* Copyright (c) 2012-2016 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.
|
|
||||||
*/
|
|
||||||
using Antlr4.Runtime.Atn;
|
|
||||||
using Antlr4.Runtime.Sharpen;
|
|
||||||
|
|
||||||
namespace Antlr4.Runtime.Atn
|
|
||||||
{
|
|
||||||
/// <author>Sam Harwell</author>
|
|
||||||
public class OrderedATNConfigSet : ATNConfigSet
|
|
||||||
{
|
|
||||||
public OrderedATNConfigSet()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
public OrderedATNConfigSet(ATNConfigSet set, bool @readonly)
|
|
||||||
: base(set, @readonly)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
public override ATNConfigSet Clone(bool @readonly)
|
|
||||||
{
|
|
||||||
Antlr4.Runtime.Atn.OrderedATNConfigSet copy = new Antlr4.Runtime.Atn.OrderedATNConfigSet(this, @readonly);
|
|
||||||
if (!@readonly && this.IsReadOnly)
|
|
||||||
{
|
|
||||||
copy.AddAll(this);
|
|
||||||
}
|
|
||||||
return copy;
|
|
||||||
}
|
|
||||||
|
|
||||||
protected internal override long GetKey(ATNConfig e)
|
|
||||||
{
|
|
||||||
return e.GetHashCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
protected internal override bool CanMerge(ATNConfig left, long leftKey, ATNConfig right)
|
|
||||||
{
|
|
||||||
return left.Equals(right);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -6,6 +6,7 @@ using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Atn;
|
using Antlr4.Runtime.Atn;
|
||||||
using Antlr4.Runtime.Dfa;
|
using Antlr4.Runtime.Dfa;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
|
@ -19,7 +20,7 @@ namespace Antlr4.Runtime
|
||||||
/// <author>Sam Harwell</author>
|
/// <author>Sam Harwell</author>
|
||||||
public class BaseErrorListener : IParserErrorListener
|
public class BaseErrorListener : IParserErrorListener
|
||||||
{
|
{
|
||||||
public virtual void SyntaxError(IRecognizer recognizer, IToken offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
public virtual void SyntaxError(TextWriter output, IRecognizer recognizer, IToken offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -371,6 +371,7 @@ namespace Antlr4.Runtime
|
||||||
this._tokenSource = tokenSource;
|
this._tokenSource = tokenSource;
|
||||||
tokens.Clear();
|
tokens.Clear();
|
||||||
p = -1;
|
p = -1;
|
||||||
|
this.fetchedEOF = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual IList<IToken> GetTokens()
|
public virtual IList<IToken> GetTokens()
|
||||||
|
|
|
@ -7,6 +7,7 @@
|
||||||
|
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
|
@ -38,9 +39,9 @@ namespace Antlr4.Runtime
|
||||||
/// line <em>line</em>:<em>charPositionInLine</em> <em>msg</em>
|
/// line <em>line</em>:<em>charPositionInLine</em> <em>msg</em>
|
||||||
/// </pre>
|
/// </pre>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public virtual void SyntaxError(IRecognizer recognizer, Symbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
public virtual void SyntaxError(TextWriter output, IRecognizer recognizer, Symbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
||||||
{
|
{
|
||||||
System.Console.Error.WriteLine("line " + line + ":" + charPositionInLine + " " + msg);
|
output.WriteLine("line " + line + ":" + charPositionInLine + " " + msg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -265,12 +265,8 @@ namespace Antlr4.Runtime
|
||||||
ITokenStream tokens = ((ITokenStream)recognizer.InputStream);
|
ITokenStream tokens = ((ITokenStream)recognizer.InputStream);
|
||||||
int la = tokens.LA(1);
|
int la = tokens.LA(1);
|
||||||
// try cheaper subset first; might get lucky. seems to shave a wee bit off
|
// try cheaper subset first; might get lucky. seems to shave a wee bit off
|
||||||
if (recognizer.Atn.NextTokens(s).Contains(la) || la == TokenConstants.EOF)
|
var nextTokens = recognizer.Atn.NextTokens(s);
|
||||||
{
|
if (nextTokens.Contains(TokenConstants.EPSILON) || nextTokens.Contains(la))
|
||||||
return;
|
|
||||||
}
|
|
||||||
// Return but don't end recovery. only do that upon valid token match
|
|
||||||
if (recognizer.IsExpectedToken(la))
|
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
*/
|
*/
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
|
||||||
namespace Antlr4.Runtime.Dfa
|
namespace Antlr4.Runtime.Dfa
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
*/
|
*/
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
|
@ -30,6 +31,9 @@ namespace Antlr4.Runtime
|
||||||
/// in-line, without returning from the surrounding rule (via the single
|
/// in-line, without returning from the surrounding rule (via the single
|
||||||
/// token insertion and deletion mechanism).</p>
|
/// token insertion and deletion mechanism).</p>
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
|
/// <param name="output">
|
||||||
|
/// Where the error should be written.
|
||||||
|
/// </param>
|
||||||
/// <param name="recognizer">
|
/// <param name="recognizer">
|
||||||
/// What parser got the error. From this
|
/// What parser got the error. From this
|
||||||
/// object, you can access the context as well
|
/// object, you can access the context as well
|
||||||
|
@ -52,6 +56,6 @@ namespace Antlr4.Runtime
|
||||||
/// the parser was able to recover in line without exiting the
|
/// the parser was able to recover in line without exiting the
|
||||||
/// surrounding rule.
|
/// surrounding rule.
|
||||||
/// </param>
|
/// </param>
|
||||||
void SyntaxError(IRecognizer recognizer, TSymbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e);
|
void SyntaxError(TextWriter output, IRecognizer recognizer, TSymbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Misc;
|
using Antlr4.Runtime.Misc;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
* can be found in the LICENSE.txt file in the project root.
|
* can be found in the LICENSE.txt file in the project root.
|
||||||
*/
|
*/
|
||||||
using System;
|
using System;
|
||||||
|
using System.IO;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
|
@ -27,12 +28,16 @@ namespace Antlr4.Runtime
|
||||||
|
|
||||||
public const int Hidden = TokenConstants.HiddenChannel;
|
public const int Hidden = TokenConstants.HiddenChannel;
|
||||||
|
|
||||||
public const int MinCharValue = '\u0000';
|
public const int MinCharValue = 0x0000;
|
||||||
|
|
||||||
public const int MaxCharValue = '\uFFFE';
|
public const int MaxCharValue = 0x10FFFF;
|
||||||
|
|
||||||
private ICharStream _input;
|
private ICharStream _input;
|
||||||
|
|
||||||
|
protected readonly TextWriter Output;
|
||||||
|
|
||||||
|
protected readonly TextWriter ErrorOutput;
|
||||||
|
|
||||||
private Tuple<ITokenSource, ICharStream> _tokenFactorySourcePair;
|
private Tuple<ITokenSource, ICharStream> _tokenFactorySourcePair;
|
||||||
|
|
||||||
/// <summary>How to create token objects</summary>
|
/// <summary>How to create token objects</summary>
|
||||||
|
@ -94,9 +99,13 @@ namespace Antlr4.Runtime
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
private string _text;
|
private string _text;
|
||||||
|
|
||||||
public Lexer(ICharStream input)
|
public Lexer(ICharStream input) : this(input, Console.Out, Console.Error) { }
|
||||||
|
|
||||||
|
public Lexer(ICharStream input, TextWriter output, TextWriter errorOutput)
|
||||||
{
|
{
|
||||||
this._input = input;
|
this._input = input;
|
||||||
|
this.Output = output;
|
||||||
|
this.ErrorOutput = errorOutput;
|
||||||
this._tokenFactorySourcePair = Tuple.Create((ITokenSource)this, input);
|
this._tokenFactorySourcePair = Tuple.Create((ITokenSource)this, input);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -502,7 +511,7 @@ outer_continue: ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual string[] ModeNames
|
public virtual string[] ChannelNames
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
{
|
{
|
||||||
|
@ -510,6 +519,13 @@ outer_continue: ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public virtual string[] ModeNames
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>Return a list of all Token objects in input char stream.</summary>
|
/// <summary>Return a list of all Token objects in input char stream.</summary>
|
||||||
/// <remarks>
|
/// <remarks>
|
||||||
|
@ -542,22 +558,23 @@ outer_continue: ;
|
||||||
string text = _input.GetText(Interval.Of(_tokenStartCharIndex, _input.Index));
|
string text = _input.GetText(Interval.Of(_tokenStartCharIndex, _input.Index));
|
||||||
string msg = "token recognition error at: '" + GetErrorDisplay(text) + "'";
|
string msg = "token recognition error at: '" + GetErrorDisplay(text) + "'";
|
||||||
IAntlrErrorListener<int> listener = ErrorListenerDispatch;
|
IAntlrErrorListener<int> listener = ErrorListenerDispatch;
|
||||||
listener.SyntaxError(this, 0, _tokenStartLine, _tokenStartColumn, msg, e);
|
listener.SyntaxError(ErrorOutput, this, 0, _tokenStartLine, _tokenStartColumn, msg, e);
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual string GetErrorDisplay(string s)
|
public virtual string GetErrorDisplay(string s)
|
||||||
{
|
{
|
||||||
StringBuilder buf = new StringBuilder();
|
StringBuilder buf = new StringBuilder();
|
||||||
foreach (char c in s.ToCharArray())
|
for (var i = 0; i < s.Length; ) {
|
||||||
{
|
var codePoint = Char.ConvertToUtf32(s, i);
|
||||||
buf.Append(GetErrorDisplay(c));
|
buf.Append(GetErrorDisplay(codePoint));
|
||||||
|
i += (codePoint > 0xFFFF) ? 2 : 1;
|
||||||
}
|
}
|
||||||
return buf.ToString();
|
return buf.ToString();
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual string GetErrorDisplay(int c)
|
public virtual string GetErrorDisplay(int c)
|
||||||
{
|
{
|
||||||
string s = ((char)c).ToString();
|
string s;
|
||||||
switch (c)
|
switch (c)
|
||||||
{
|
{
|
||||||
case TokenConstants.EOF:
|
case TokenConstants.EOF:
|
||||||
|
@ -583,6 +600,12 @@ outer_continue: ;
|
||||||
s = "\\r";
|
s = "\\r";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
default:
|
||||||
|
{
|
||||||
|
s = Char.ConvertFromUtf32(c);
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,23 +13,31 @@ using Antlr4.Runtime.Sharpen;
|
||||||
|
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
public class LexerInterpreter : Lexer
|
public class LexerInterpreter: Lexer
|
||||||
{
|
{
|
||||||
private readonly string grammarFileName;
|
private readonly string grammarFileName;
|
||||||
|
|
||||||
private readonly ATN atn;
|
private readonly ATN atn;
|
||||||
|
|
||||||
private readonly string[] ruleNames;
|
private readonly string[] ruleNames;
|
||||||
|
|
||||||
private readonly string[] modeNames;
|
private readonly string[] channelNames;
|
||||||
|
|
||||||
|
private readonly string[] modeNames;
|
||||||
|
|
||||||
[NotNull]
|
[NotNull]
|
||||||
private readonly IVocabulary vocabulary;
|
private readonly IVocabulary vocabulary;
|
||||||
|
|
||||||
protected DFA[] decisionToDFA;
|
protected DFA[] decisionToDFA;
|
||||||
protected PredictionContextCache sharedContextCache = new PredictionContextCache();
|
protected PredictionContextCache sharedContextCache = new PredictionContextCache();
|
||||||
|
|
||||||
|
[Obsolete("Use constructor with channelNames argument")]
|
||||||
public LexerInterpreter(string grammarFileName, IVocabulary vocabulary, IEnumerable<string> ruleNames, IEnumerable<string> modeNames, ATN atn, ICharStream input)
|
public LexerInterpreter(string grammarFileName, IVocabulary vocabulary, IEnumerable<string> ruleNames, IEnumerable<string> modeNames, ATN atn, ICharStream input)
|
||||||
|
: this(grammarFileName, vocabulary, ruleNames, new string[0], modeNames, atn, input)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
public LexerInterpreter(string grammarFileName, IVocabulary vocabulary, IEnumerable<string> ruleNames, IEnumerable<string> channelNames, IEnumerable<string> modeNames, ATN atn, ICharStream input)
|
||||||
: base(input)
|
: base(input)
|
||||||
{
|
{
|
||||||
if (atn.grammarType != ATNType.Lexer)
|
if (atn.grammarType != ATNType.Lexer)
|
||||||
|
@ -39,14 +47,15 @@ namespace Antlr4.Runtime
|
||||||
this.grammarFileName = grammarFileName;
|
this.grammarFileName = grammarFileName;
|
||||||
this.atn = atn;
|
this.atn = atn;
|
||||||
this.ruleNames = ruleNames.ToArray();
|
this.ruleNames = ruleNames.ToArray();
|
||||||
|
this.channelNames = channelNames.ToArray();
|
||||||
this.modeNames = modeNames.ToArray();
|
this.modeNames = modeNames.ToArray();
|
||||||
this.vocabulary = vocabulary;
|
this.vocabulary = vocabulary;
|
||||||
this.decisionToDFA = new DFA[atn.NumberOfDecisions];
|
this.decisionToDFA = new DFA[atn.NumberOfDecisions];
|
||||||
for (int i = 0; i < decisionToDFA.Length; i++)
|
for (int i = 0; i < decisionToDFA.Length; i++)
|
||||||
{
|
{
|
||||||
decisionToDFA[i] = new DFA(atn.GetDecisionState(i), i);
|
decisionToDFA[i] = new DFA(atn.GetDecisionState(i), i);
|
||||||
}
|
}
|
||||||
this.Interpreter = new LexerATNSimulator(this, atn, decisionToDFA, sharedContextCache);
|
this.Interpreter = new LexerATNSimulator(this, atn, decisionToDFA, sharedContextCache);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override ATN Atn
|
public override ATN Atn
|
||||||
|
@ -73,6 +82,14 @@ namespace Antlr4.Runtime
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public override string[] ChannelNames
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return channelNames;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public override string[] ModeNames
|
public override string[] ModeNames
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
|
|
|
@ -1,58 +0,0 @@
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
|
|
||||||
namespace Antlr4.Runtime.Misc
|
|
||||||
{
|
|
||||||
public class DoubleKeyMap<K1, K2, V>
|
|
||||||
{
|
|
||||||
Dictionary<K1, Dictionary<K2, V>> data = new Dictionary<K1, Dictionary<K2, V>>();
|
|
||||||
|
|
||||||
public V put(K1 k1, K2 k2, V v)
|
|
||||||
{
|
|
||||||
Dictionary<K2, V> data2 = data.get(k1);
|
|
||||||
V prev = null;
|
|
||||||
if (data2 == null)
|
|
||||||
{
|
|
||||||
data2 = new Dict<K2, V>();
|
|
||||||
data.put(k1, data2);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
prev = data2.get(k2);
|
|
||||||
}
|
|
||||||
data2.put(k2, v);
|
|
||||||
return prev;
|
|
||||||
}
|
|
||||||
|
|
||||||
public V get(K1 k1, K2 k2)
|
|
||||||
{
|
|
||||||
Dictionary<K2, V> data2 = data.get(k1);
|
|
||||||
if (data2 == null) return null;
|
|
||||||
return data2.get(k2);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Dictionary<K2, V> get(K1 k1) { return data.get(k1); }
|
|
||||||
|
|
||||||
/** Get all values associated with primary key */
|
|
||||||
public ICollection<V> values(K1 k1)
|
|
||||||
{
|
|
||||||
Dictionary<K2, V> data2 = data.get(k1);
|
|
||||||
if (data2 == null) return null;
|
|
||||||
return data2.values();
|
|
||||||
}
|
|
||||||
|
|
||||||
/** get all primary keys */
|
|
||||||
public HashSet<K1> keySet()
|
|
||||||
{
|
|
||||||
return data.keySet();
|
|
||||||
}
|
|
||||||
|
|
||||||
/** get all secondary keys associated with a primary key */
|
|
||||||
public HashSet<K2> keySet(K1 k1)
|
|
||||||
{
|
|
||||||
Dictionary<K2, V> data2 = data.get(k1);
|
|
||||||
if (data2 == null) return null;
|
|
||||||
return data2.keySet();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -2,6 +2,7 @@
|
||||||
* Use of this file is governed by the BSD 3-clause license that
|
* 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.
|
* can be found in the LICENSE.txt file in the project root.
|
||||||
*/
|
*/
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
|
||||||
|
|
|
@ -354,7 +354,7 @@ namespace Antlr4.Runtime.Misc
|
||||||
}
|
}
|
||||||
foreach (Transition transition in state.transitions)
|
foreach (Transition transition in state.transitions)
|
||||||
{
|
{
|
||||||
if (transition.TransitionType != TransitionType.Rule)
|
if (transition.TransitionType != TransitionType.RULE)
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -459,7 +459,7 @@ namespace Antlr4.Runtime.Misc
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
#if PORTABLE
|
#if PORTABLE || DOTNETCORE
|
||||||
public interface ICustomAttributeProvider
|
public interface ICustomAttributeProvider
|
||||||
{
|
{
|
||||||
object[] GetCustomAttributes(Type attributeType, bool inherit);
|
object[] GetCustomAttributes(Type attributeType, bool inherit);
|
||||||
|
@ -646,7 +646,11 @@ namespace Antlr4.Runtime.Misc
|
||||||
StringBuilder errors = new StringBuilder();
|
StringBuilder errors = new StringBuilder();
|
||||||
foreach (Tuple<RuleDependencyAttribute, ICustomAttributeProvider> dependency in dependencies)
|
foreach (Tuple<RuleDependencyAttribute, ICustomAttributeProvider> dependency in dependencies)
|
||||||
{
|
{
|
||||||
if (!dependency.Item1.Recognizer.IsAssignableFrom(recognizerType))
|
#if DOTNETCORE
|
||||||
|
if (!dependency.Item1.Recognizer.GetTypeInfo().IsAssignableFrom(recognizerType))
|
||||||
|
#else
|
||||||
|
if (!dependency.Item1.Recognizer.IsAssignableFrom(recognizerType))
|
||||||
|
#endif
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -773,7 +777,11 @@ namespace Antlr4.Runtime.Misc
|
||||||
private static int[] GetRuleVersions(Type recognizerClass, string[] ruleNames)
|
private static int[] GetRuleVersions(Type recognizerClass, string[] ruleNames)
|
||||||
{
|
{
|
||||||
int[] versions = new int[ruleNames.Length];
|
int[] versions = new int[ruleNames.Length];
|
||||||
|
#if DOTNETCORE
|
||||||
|
FieldInfo[] fields = recognizerClass.GetTypeInfo().GetFields();
|
||||||
|
#else
|
||||||
FieldInfo[] fields = recognizerClass.GetFields();
|
FieldInfo[] fields = recognizerClass.GetFields();
|
||||||
|
#endif
|
||||||
foreach (FieldInfo field in fields)
|
foreach (FieldInfo field in fields)
|
||||||
{
|
{
|
||||||
bool isStatic = field.IsStatic;
|
bool isStatic = field.IsStatic;
|
||||||
|
@ -805,7 +813,11 @@ namespace Antlr4.Runtime.Misc
|
||||||
#endif
|
#endif
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
#if DOTNETCORE
|
||||||
|
RuleVersionAttribute ruleVersion = ruleMethod.GetCustomAttribute<RuleVersionAttribute>();
|
||||||
|
#else
|
||||||
RuleVersionAttribute ruleVersion = (RuleVersionAttribute)Attribute.GetCustomAttribute(ruleMethod, typeof(RuleVersionAttribute));
|
RuleVersionAttribute ruleVersion = (RuleVersionAttribute)Attribute.GetCustomAttribute(ruleMethod, typeof(RuleVersionAttribute));
|
||||||
|
#endif
|
||||||
int version = ruleVersion != null ? ruleVersion.Version : 0;
|
int version = ruleVersion != null ? ruleVersion.Version : 0;
|
||||||
versions[index] = version;
|
versions[index] = version;
|
||||||
}
|
}
|
||||||
|
@ -832,10 +844,18 @@ namespace Antlr4.Runtime.Misc
|
||||||
|
|
||||||
private static MethodInfo GetRuleMethod(Type recognizerClass, string name)
|
private static MethodInfo GetRuleMethod(Type recognizerClass, string name)
|
||||||
{
|
{
|
||||||
|
#if DOTNETCORE
|
||||||
|
MethodInfo[] declaredMethods = recognizerClass.GetTypeInfo().GetMethods();
|
||||||
|
#else
|
||||||
MethodInfo[] declaredMethods = recognizerClass.GetMethods();
|
MethodInfo[] declaredMethods = recognizerClass.GetMethods();
|
||||||
|
#endif
|
||||||
foreach (MethodInfo method in declaredMethods)
|
foreach (MethodInfo method in declaredMethods)
|
||||||
{
|
{
|
||||||
if (method.Name.Equals(name) && Attribute.IsDefined(method, typeof(RuleVersionAttribute)))
|
#if DOTNETCORE
|
||||||
|
if (method.Name.Equals(name) && method.IsDefined(typeof(RuleVersionAttribute)))
|
||||||
|
#else
|
||||||
|
if (method.Name.Equals(name) && Attribute.IsDefined(method, typeof(RuleVersionAttribute)))
|
||||||
|
#endif
|
||||||
{
|
{
|
||||||
return method;
|
return method;
|
||||||
}
|
}
|
||||||
|
@ -845,7 +865,11 @@ namespace Antlr4.Runtime.Misc
|
||||||
|
|
||||||
private static string[] GetRuleNames(Type recognizerClass)
|
private static string[] GetRuleNames(Type recognizerClass)
|
||||||
{
|
{
|
||||||
|
#if DOTNETCORE
|
||||||
|
FieldInfo ruleNames = recognizerClass.GetTypeInfo().GetField("ruleNames");
|
||||||
|
#else
|
||||||
FieldInfo ruleNames = recognizerClass.GetField("ruleNames");
|
FieldInfo ruleNames = recognizerClass.GetField("ruleNames");
|
||||||
|
#endif
|
||||||
return (string[])ruleNames.GetValue(null);
|
return (string[])ruleNames.GetValue(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -853,20 +877,36 @@ namespace Antlr4.Runtime.Misc
|
||||||
{
|
{
|
||||||
IList<Tuple<RuleDependencyAttribute, ICustomAttributeProvider>> result = new ArrayList<Tuple<RuleDependencyAttribute, ICustomAttributeProvider>>();
|
IList<Tuple<RuleDependencyAttribute, ICustomAttributeProvider>> result = new ArrayList<Tuple<RuleDependencyAttribute, ICustomAttributeProvider>>();
|
||||||
|
|
||||||
|
#if DOTNETCORE
|
||||||
|
GetElementDependencies(AsCustomAttributeProvider(clazz.GetTypeInfo()), result);
|
||||||
|
#else
|
||||||
GetElementDependencies(AsCustomAttributeProvider(clazz), result);
|
GetElementDependencies(AsCustomAttributeProvider(clazz), result);
|
||||||
|
#endif
|
||||||
|
#if DOTNETCORE
|
||||||
|
foreach (ConstructorInfo ctor in clazz.GetTypeInfo().GetConstructors(AllDeclaredMembers))
|
||||||
|
#else
|
||||||
foreach (ConstructorInfo ctor in clazz.GetConstructors(AllDeclaredMembers))
|
foreach (ConstructorInfo ctor in clazz.GetConstructors(AllDeclaredMembers))
|
||||||
|
#endif
|
||||||
{
|
{
|
||||||
GetElementDependencies(AsCustomAttributeProvider(ctor), result);
|
GetElementDependencies(AsCustomAttributeProvider(ctor), result);
|
||||||
foreach (ParameterInfo parameter in ctor.GetParameters())
|
foreach (ParameterInfo parameter in ctor.GetParameters())
|
||||||
GetElementDependencies(AsCustomAttributeProvider(parameter), result);
|
GetElementDependencies(AsCustomAttributeProvider(parameter), result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if DOTNETCORE
|
||||||
|
foreach (FieldInfo field in clazz.GetTypeInfo().GetFields(AllDeclaredMembers))
|
||||||
|
#else
|
||||||
foreach (FieldInfo field in clazz.GetFields(AllDeclaredMembers))
|
foreach (FieldInfo field in clazz.GetFields(AllDeclaredMembers))
|
||||||
|
#endif
|
||||||
{
|
{
|
||||||
GetElementDependencies(AsCustomAttributeProvider(field), result);
|
GetElementDependencies(AsCustomAttributeProvider(field), result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if DOTNETCORE
|
||||||
|
foreach (MethodInfo method in clazz.GetTypeInfo().GetMethods(AllDeclaredMembers))
|
||||||
|
#else
|
||||||
foreach (MethodInfo method in clazz.GetMethods(AllDeclaredMembers))
|
foreach (MethodInfo method in clazz.GetMethods(AllDeclaredMembers))
|
||||||
|
#endif
|
||||||
{
|
{
|
||||||
GetElementDependencies(AsCustomAttributeProvider(method), result);
|
GetElementDependencies(AsCustomAttributeProvider(method), result);
|
||||||
#if COMPACT
|
#if COMPACT
|
||||||
|
@ -922,12 +962,21 @@ namespace Antlr4.Runtime.Misc
|
||||||
|
|
||||||
private static string GetSerializedATN(Type recognizerClass)
|
private static string GetSerializedATN(Type recognizerClass)
|
||||||
{
|
{
|
||||||
|
#if DOTNETCORE
|
||||||
|
FieldInfo serializedAtnField = recognizerClass.GetTypeInfo().GetField("_serializedATN", AllDeclaredStaticMembers);
|
||||||
|
#else
|
||||||
FieldInfo serializedAtnField = recognizerClass.GetField("_serializedATN", AllDeclaredStaticMembers);
|
FieldInfo serializedAtnField = recognizerClass.GetField("_serializedATN", AllDeclaredStaticMembers);
|
||||||
|
#endif
|
||||||
if (serializedAtnField != null)
|
if (serializedAtnField != null)
|
||||||
return (string)serializedAtnField.GetValue(null);
|
return (string)serializedAtnField.GetValue(null);
|
||||||
|
|
||||||
|
#if DOTNETCORE
|
||||||
|
if (recognizerClass.GetTypeInfo().BaseType != null)
|
||||||
|
return GetSerializedATN(recognizerClass.GetTypeInfo().BaseType);
|
||||||
|
#else
|
||||||
if (recognizerClass.BaseType != null)
|
if (recognizerClass.BaseType != null)
|
||||||
return GetSerializedATN(recognizerClass.BaseType);
|
return GetSerializedATN(recognizerClass.BaseType);
|
||||||
|
#endif
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
|
@ -131,19 +131,5 @@ namespace Antlr4.Runtime.Misc
|
||||||
}
|
}
|
||||||
return m;
|
return m;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static char[] ToCharArray(ArrayList<int> data)
|
|
||||||
{
|
|
||||||
if (data == null)
|
|
||||||
{
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
char[] cdata = new char[data.Count];
|
|
||||||
for (int i = 0; i < data.Count; i++)
|
|
||||||
{
|
|
||||||
cdata[i] = (char)data[i];
|
|
||||||
}
|
|
||||||
return cdata;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
* can be found in the LICENSE.txt file in the project root.
|
* can be found in the LICENSE.txt file in the project root.
|
||||||
*/
|
*/
|
||||||
using System;
|
using System;
|
||||||
|
using System.IO;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using Antlr4.Runtime.Atn;
|
using Antlr4.Runtime.Atn;
|
||||||
|
@ -21,14 +22,20 @@ namespace Antlr4.Runtime
|
||||||
#if !PORTABLE
|
#if !PORTABLE
|
||||||
public class TraceListener : IParseTreeListener
|
public class TraceListener : IParseTreeListener
|
||||||
{
|
{
|
||||||
|
private readonly TextWriter Output;
|
||||||
|
|
||||||
|
public TraceListener(TextWriter output) {
|
||||||
|
Output = output;
|
||||||
|
}
|
||||||
|
|
||||||
public virtual void EnterEveryRule(ParserRuleContext ctx)
|
public virtual void EnterEveryRule(ParserRuleContext ctx)
|
||||||
{
|
{
|
||||||
System.Console.Out.WriteLine("enter " + this._enclosing.RuleNames[ctx.RuleIndex] + ", LT(1)=" + this._enclosing._input.LT(1).Text);
|
Output.WriteLine("enter " + this._enclosing.RuleNames[ctx.RuleIndex] + ", LT(1)=" + this._enclosing._input.LT(1).Text);
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual void ExitEveryRule(ParserRuleContext ctx)
|
public virtual void ExitEveryRule(ParserRuleContext ctx)
|
||||||
{
|
{
|
||||||
System.Console.Out.WriteLine("exit " + this._enclosing.RuleNames[ctx.RuleIndex] + ", LT(1)=" + this._enclosing._input.LT(1).Text);
|
Output.WriteLine("exit " + this._enclosing.RuleNames[ctx.RuleIndex] + ", LT(1)=" + this._enclosing._input.LT(1).Text);
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual void VisitErrorNode(IErrorNode node)
|
public virtual void VisitErrorNode(IErrorNode node)
|
||||||
|
@ -39,7 +46,7 @@ namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
ParserRuleContext parent = (ParserRuleContext)((IRuleNode)node.Parent).RuleContext;
|
ParserRuleContext parent = (ParserRuleContext)((IRuleNode)node.Parent).RuleContext;
|
||||||
IToken token = node.Symbol;
|
IToken token = node.Symbol;
|
||||||
System.Console.Out.WriteLine("consume " + token + " rule " + this._enclosing.RuleNames[parent.RuleIndex]);
|
Output.WriteLine("consume " + token + " rule " + this._enclosing.RuleNames[parent.RuleIndex]);
|
||||||
}
|
}
|
||||||
|
|
||||||
internal TraceListener(Parser _enclosing)
|
internal TraceListener(Parser _enclosing)
|
||||||
|
@ -161,9 +168,16 @@ namespace Antlr4.Runtime
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
private int _syntaxErrors;
|
private int _syntaxErrors;
|
||||||
|
|
||||||
public Parser(ITokenStream input)
|
protected readonly TextWriter Output;
|
||||||
|
protected readonly TextWriter ErrorOutput;
|
||||||
|
|
||||||
|
public Parser(ITokenStream input) : this(input, Console.Out, Console.Error) { }
|
||||||
|
|
||||||
|
public Parser(ITokenStream input, TextWriter output, TextWriter errorOutput)
|
||||||
{
|
{
|
||||||
TokenStream = input;
|
TokenStream = input;
|
||||||
|
Output = output;
|
||||||
|
ErrorOutput = errorOutput;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>reset the parser's state</summary>
|
/// <summary>reset the parser's state</summary>
|
||||||
|
@ -676,7 +690,7 @@ namespace Antlr4.Runtime
|
||||||
charPositionInLine = offendingToken.Column;
|
charPositionInLine = offendingToken.Column;
|
||||||
}
|
}
|
||||||
IAntlrErrorListener<IToken> listener = ((IParserErrorListener)ErrorListenerDispatch);
|
IAntlrErrorListener<IToken> listener = ((IParserErrorListener)ErrorListenerDispatch);
|
||||||
listener.SyntaxError(this, offendingToken, line, charPositionInLine, msg, e);
|
listener.SyntaxError(ErrorOutput, this, offendingToken, line, charPositionInLine, msg, e);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -1143,10 +1157,10 @@ namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
if (seenOne)
|
if (seenOne)
|
||||||
{
|
{
|
||||||
System.Console.Out.WriteLine();
|
Output.WriteLine();
|
||||||
}
|
}
|
||||||
System.Console.Out.WriteLine("Decision " + dfa.decision + ":");
|
Output.WriteLine("Decision " + dfa.decision + ":");
|
||||||
System.Console.Out.Write(dfa.ToString(Vocabulary));
|
Output.Write(dfa.ToString(Vocabulary));
|
||||||
seenOne = true;
|
seenOne = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -116,7 +116,18 @@ namespace Antlr4.Runtime
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>COPY a ctx (I'm deliberately not using copy constructor)</summary>
|
/// <summary>
|
||||||
|
/// COPY a ctx (I'm deliberately not using copy constructor) to avoid
|
||||||
|
/// confusion with creating node with parent. Does not copy children.
|
||||||
|
///
|
||||||
|
/// This is used in the generated parser code to flip a generic XContext
|
||||||
|
/// node for rule X to a YContext for alt label Y. In that sense, it is
|
||||||
|
/// not really a generic copy function.
|
||||||
|
///
|
||||||
|
/// If we do an error sync() at start of a rule, we might add error nodes
|
||||||
|
/// to the generic XContext so this function must copy those nodes to
|
||||||
|
/// the YContext as well else they are lost!
|
||||||
|
/// </summary>
|
||||||
public virtual void CopyFrom(Antlr4.Runtime.ParserRuleContext ctx)
|
public virtual void CopyFrom(Antlr4.Runtime.ParserRuleContext ctx)
|
||||||
{
|
{
|
||||||
// from RuleContext
|
// from RuleContext
|
||||||
|
@ -124,6 +135,22 @@ namespace Antlr4.Runtime
|
||||||
this.invokingState = ctx.invokingState;
|
this.invokingState = ctx.invokingState;
|
||||||
this._start = ctx._start;
|
this._start = ctx._start;
|
||||||
this._stop = ctx._stop;
|
this._stop = ctx._stop;
|
||||||
|
|
||||||
|
// copy any error nodes to alt label node
|
||||||
|
if (ctx.children != null)
|
||||||
|
{
|
||||||
|
children = new List<IParseTree>();
|
||||||
|
// reset parent pointer for any error nodes
|
||||||
|
foreach (var child in ctx.children)
|
||||||
|
{
|
||||||
|
var errorChildNode = child as ErrorNodeImpl;
|
||||||
|
if (errorChildNode != null)
|
||||||
|
{
|
||||||
|
children.Add(errorChildNode);
|
||||||
|
errorChildNode.Parent = this;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public ParserRuleContext(Antlr4.Runtime.ParserRuleContext parent, int invokingStateNumber)
|
public ParserRuleContext(Antlr4.Runtime.ParserRuleContext parent, int invokingStateNumber)
|
||||||
|
@ -252,7 +279,7 @@ namespace Antlr4.Runtime
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if NET45PLUS
|
#if (NET45PLUS && !DOTNETCORE)
|
||||||
public virtual IReadOnlyList<ITerminalNode> GetTokens(int ttype)
|
public virtual IReadOnlyList<ITerminalNode> GetTokens(int ttype)
|
||||||
#else
|
#else
|
||||||
public virtual ITerminalNode[] GetTokens(int ttype)
|
public virtual ITerminalNode[] GetTokens(int ttype)
|
||||||
|
@ -283,7 +310,7 @@ namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
return Collections.EmptyList<ITerminalNode>();
|
return Collections.EmptyList<ITerminalNode>();
|
||||||
}
|
}
|
||||||
#if NET45PLUS
|
#if (NET45PLUS && !DOTNETCORE)
|
||||||
return tokens;
|
return tokens;
|
||||||
#else
|
#else
|
||||||
return tokens.ToArray();
|
return tokens.ToArray();
|
||||||
|
@ -296,7 +323,7 @@ namespace Antlr4.Runtime
|
||||||
return GetChild<T>(i);
|
return GetChild<T>(i);
|
||||||
}
|
}
|
||||||
|
|
||||||
#if NET45PLUS
|
#if (NET45PLUS && !DOTNETCORE)
|
||||||
public virtual IReadOnlyList<T> GetRuleContexts<T>()
|
public virtual IReadOnlyList<T> GetRuleContexts<T>()
|
||||||
where T : Antlr4.Runtime.ParserRuleContext
|
where T : Antlr4.Runtime.ParserRuleContext
|
||||||
#else
|
#else
|
||||||
|
@ -324,7 +351,7 @@ namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
return Collections.EmptyList<T>();
|
return Collections.EmptyList<T>();
|
||||||
}
|
}
|
||||||
#if NET45PLUS
|
#if (NET45PLUS && !DOTNETCORE)
|
||||||
return contexts;
|
return contexts;
|
||||||
#else
|
#else
|
||||||
return contexts.ToArray();
|
return contexts.ToArray();
|
||||||
|
|
|
@ -42,8 +42,8 @@ using System.Runtime.InteropServices;
|
||||||
// You can specify all the values or you can default the Build and Revision Numbers
|
// You can specify all the values or you can default the Build and Revision Numbers
|
||||||
// by using the '*' as shown below:
|
// by using the '*' as shown below:
|
||||||
// [assembly: AssemblyVersion("1.0.*")]
|
// [assembly: AssemblyVersion("1.0.*")]
|
||||||
[assembly: AssemblyVersion("4.6.0")]
|
[assembly: AssemblyVersion("4.6.1")]
|
||||||
#if !COMPACT
|
#if !COMPACT
|
||||||
[assembly: AssemblyFileVersion("4.6.0")]
|
[assembly: AssemblyFileVersion("4.6.1")]
|
||||||
[assembly: AssemblyInformationalVersion("4.6.0")]
|
[assembly: AssemblyInformationalVersion("4.6.1")]
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
*/
|
*/
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
namespace Antlr4.Runtime
|
namespace Antlr4.Runtime
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -35,11 +36,11 @@ namespace Antlr4.Runtime
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual void SyntaxError(IRecognizer recognizer, Symbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
public virtual void SyntaxError(TextWriter output, IRecognizer recognizer, Symbol offendingSymbol, int line, int charPositionInLine, string msg, RecognitionException e)
|
||||||
{
|
{
|
||||||
foreach (IAntlrErrorListener<Symbol> listener in delegates)
|
foreach (IAntlrErrorListener<Symbol> listener in delegates)
|
||||||
{
|
{
|
||||||
listener.SyntaxError(recognizer, offendingSymbol, line, charPositionInLine, msg, e);
|
listener.SyntaxError(output, recognizer, offendingSymbol, line, charPositionInLine, msg, e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
/* Copyright (c) 2012-2016 The ANTLR Project. All rights reserved.
|
/* Copyright (c) 2012-2016 The ANTLR Project. All rights reserved.
|
||||||
* Use of this file is governed by the BSD 3-clause license that
|
* 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.
|
* can be found in the LICENSE.txt file in the project root.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#if PORTABLE
|
#if PORTABLE || DOTNETCORE
|
||||||
|
|
||||||
namespace System
|
namespace System
|
||||||
{
|
{
|
||||||
|
@ -14,3 +14,4 @@ namespace System
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -28,7 +28,6 @@ using System;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Runtime.Serialization;
|
|
||||||
|
|
||||||
namespace Antlr4.Runtime.Sharpen
|
namespace Antlr4.Runtime.Sharpen
|
||||||
{
|
{
|
||||||
|
|
|
@ -2,7 +2,11 @@
|
||||||
* Use of this file is governed by the BSD 3-clause license that
|
* 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.
|
* can be found in the LICENSE.txt file in the project root.
|
||||||
*/
|
*/
|
||||||
|
#if NET40PLUS
|
||||||
|
using System.Collections.Concurrent;
|
||||||
|
#else
|
||||||
using Antlr4.Runtime.Sharpen;
|
using Antlr4.Runtime.Sharpen;
|
||||||
|
#endif
|
||||||
|
|
||||||
namespace Antlr4.Runtime.Tree
|
namespace Antlr4.Runtime.Tree
|
||||||
{
|
{
|
||||||
|
|
|
@ -138,7 +138,7 @@ namespace Antlr4.Runtime.Tree.Pattern
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[System.Serializable]
|
[System.Serializable]
|
||||||
public class StartRuleDoesNotConsumeFullPattern : Exception
|
public class StartRuleDoesNotConsumeFullPattern : Exception
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,115 +1,151 @@
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
// <auto-generated>
|
// <auto-generated>
|
||||||
// This code was generated by a tool.
|
// This code was generated by a tool.
|
||||||
// ANTLR Version: 4.4.1-dev
|
// ANTLR Version: 4.6.1
|
||||||
//
|
//
|
||||||
// Changes to this file may cause incorrect behavior and will be lost if
|
// Changes to this file may cause incorrect behavior and will be lost if
|
||||||
// the code is regenerated.
|
// the code is regenerated.
|
||||||
// </auto-generated>
|
// </auto-generated>
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Generated from /Users/ericvergnaud/Development/antlr4/antlr/antlr4-csharp/runtime/CSharp/Antlr4.Runtime/Tree/Xpath/XPathLexer.g4 by ANTLR 4.4.1-dev
|
|
||||||
|
|
||||||
// Unreachable code detected
|
// Unreachable code detected
|
||||||
#pragma warning disable 0162
|
#pragma warning disable 0162
|
||||||
// The variable '...' is assigned but its value is never used
|
// The variable '...' is assigned but its value is never used
|
||||||
#pragma warning disable 0219
|
#pragma warning disable 0219
|
||||||
// Missing XML comment for publicly visible type or member '...'
|
// Missing XML comment for publicly visible type or member '...'
|
||||||
#pragma warning disable 1591
|
#pragma warning disable 1591
|
||||||
|
// Ambiguous reference in cref attribute
|
||||||
|
#pragma warning disable 419
|
||||||
|
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
|
|
||||||
|
using System;
|
||||||
|
using System.Text;
|
||||||
using Antlr4.Runtime;
|
using Antlr4.Runtime;
|
||||||
using Antlr4.Runtime.Atn;
|
using Antlr4.Runtime.Atn;
|
||||||
using Antlr4.Runtime.Misc;
|
using Antlr4.Runtime.Misc;
|
||||||
using DFA = Antlr4.Runtime.Dfa.DFA;
|
using DFA = Antlr4.Runtime.Dfa.DFA;
|
||||||
|
|
||||||
|
[System.CodeDom.Compiler.GeneratedCode("ANTLR", "4.6.1")]
|
||||||
[System.CLSCompliant(false)]
|
[System.CLSCompliant(false)]
|
||||||
public partial class XPathLexer : Lexer {
|
public partial class XPathLexer : Lexer
|
||||||
public const int
|
{
|
||||||
TokenRef=1, RuleRef=2, Anywhere=3, Root=4, Wildcard=5, Bang=6, ID=7, String=8;
|
protected static DFA[] decisionToDFA;
|
||||||
public static string[] modeNames = {
|
protected static PredictionContextCache sharedContextCache = new PredictionContextCache();
|
||||||
|
public const int
|
||||||
|
TokenRef = 1, RuleRef = 2, Anywhere = 3, Root = 4, Wildcard = 5, Bang = 6, ID = 7, String = 8;
|
||||||
|
public static string[] channelNames = {
|
||||||
|
"DEFAULT_TOKEN_CHANNEL", "HIDDEN"
|
||||||
|
};
|
||||||
|
|
||||||
|
public static string[] modeNames = {
|
||||||
"DEFAULT_MODE"
|
"DEFAULT_MODE"
|
||||||
};
|
};
|
||||||
|
|
||||||
public static readonly string[] ruleNames = {
|
public static readonly string[] ruleNames = {
|
||||||
"Anywhere", "Root", "Wildcard", "Bang", "ID", "NameChar", "NameStartChar",
|
"Anywhere", "Root", "Wildcard", "Bang", "ID", "NameChar", "NameStartChar",
|
||||||
"String"
|
"String"
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
public XPathLexer(ICharStream input)
|
public XPathLexer(ICharStream input)
|
||||||
: base(input)
|
: base(input)
|
||||||
{
|
{
|
||||||
Interpreter = new LexerATNSimulator(this, _ATN, null, null);
|
Interpreter = new LexerATNSimulator(this, _ATN, decisionToDFA, sharedContextCache);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static readonly string[] _LiteralNames = {
|
private static readonly string[] _LiteralNames = {
|
||||||
null, null, null, "'//'", "'/'", "'*'", "'!'"
|
null, null, null, "'//'", "'/'", "'*'", "'!'"
|
||||||
};
|
};
|
||||||
private static readonly string[] _SymbolicNames = {
|
private static readonly string[] _SymbolicNames = {
|
||||||
null, "TokenRef", "RuleRef", "Anywhere", "Root", "Wildcard", "Bang", "ID",
|
null, "TokenRef", "RuleRef", "Anywhere", "Root", "Wildcard", "Bang", "ID",
|
||||||
"String"
|
"String"
|
||||||
};
|
};
|
||||||
public static readonly IVocabulary DefaultVocabulary = new Vocabulary(_LiteralNames, _SymbolicNames);
|
public static readonly IVocabulary DefaultVocabulary = new Vocabulary(_LiteralNames, _SymbolicNames);
|
||||||
|
|
||||||
[NotNull]
|
[NotNull]
|
||||||
public override IVocabulary Vocabulary
|
public override IVocabulary Vocabulary
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
{
|
{
|
||||||
return DefaultVocabulary;
|
return DefaultVocabulary;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public override string GrammarFileName { get { return "XPathLexer.g4"; } }
|
public override string GrammarFileName { get { return "XPathLexer.g4"; } }
|
||||||
|
|
||||||
public override string[] RuleNames { get { return ruleNames; } }
|
public override string[] RuleNames { get { return ruleNames; } }
|
||||||
|
|
||||||
public override string[] ModeNames { get { return modeNames; } }
|
public override string[] ChannelNames { get { return channelNames; } }
|
||||||
|
|
||||||
public override string SerializedAtn { get { return _serializedATN; } }
|
public override string[] ModeNames { get { return modeNames; } }
|
||||||
|
|
||||||
|
public override string SerializedAtn { get { return _serializedATN; } }
|
||||||
|
|
||||||
|
static XPathLexer()
|
||||||
|
{
|
||||||
|
decisionToDFA = new DFA[_ATN.NumberOfDecisions];
|
||||||
|
for (int i = 0; i < _ATN.NumberOfDecisions; i++)
|
||||||
|
{
|
||||||
|
decisionToDFA[i] = new DFA(_ATN.GetDecisionState(i), i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public override void Action(RuleContext _localctx, int ruleIndex, int actionIndex)
|
||||||
|
{
|
||||||
|
switch (ruleIndex)
|
||||||
|
{
|
||||||
|
case 4: ID_action(_localctx, actionIndex); break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
private void ID_action(RuleContext _localctx, int actionIndex)
|
||||||
|
{
|
||||||
|
switch (actionIndex)
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
String text = Text;
|
||||||
|
if (Char.IsUpper(text[0]))
|
||||||
|
Type = TokenRef;
|
||||||
|
else
|
||||||
|
Type = RuleRef;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string _serializedATN = _serializeATN();
|
||||||
|
private static string _serializeATN()
|
||||||
|
{
|
||||||
|
StringBuilder sb = new StringBuilder();
|
||||||
|
sb.Append("\x3\x430\xD6D1\x8206\xAD2D\x4417\xAEF1\x8D80\xAADD\x2\n\x34");
|
||||||
|
sb.Append("\b\x1\x4\x2\t\x2\x4\x3\t\x3\x4\x4\t\x4\x4\x5\t\x5\x4\x6\t\x6");
|
||||||
|
sb.Append("\x4\a\t\a\x4\b\t\b\x4\t\t\t\x3\x2\x3\x2\x3\x2\x3\x3\x3\x3\x3");
|
||||||
|
sb.Append("\x4\x3\x4\x3\x5\x3\x5\x3\x6\x3\x6\a\x6\x1F\n\x6\f\x6\xE\x6\"");
|
||||||
|
sb.Append("\v\x6\x3\x6\x3\x6\x3\a\x3\a\x5\a(\n\a\x3\b\x3\b\x3\t\x3\t\a");
|
||||||
|
sb.Append("\t.\n\t\f\t\xE\t\x31\v\t\x3\t\x3\t\x3/\x2\n\x3\x5\x5\x6\a\a");
|
||||||
|
sb.Append("\t\b\v\t\r\x2\xF\x2\x11\n\x3\x2\x4\a\x2\x32;\x61\x61\xB9\xB9");
|
||||||
|
sb.Append("\x302\x371\x2041\x2042\xF\x2\x43\\\x63|\xC2\xD8\xDA\xF8\xFA");
|
||||||
|
sb.Append("\x301\x372\x37F\x381\x2001\x200E\x200F\x2072\x2191\x2C02\x2FF1");
|
||||||
|
sb.Append("\x3003\xD801\xF902\xFDD1\xFDF2\xFFFF\x34\x2\x3\x3\x2\x2\x2\x2");
|
||||||
|
sb.Append("\x5\x3\x2\x2\x2\x2\a\x3\x2\x2\x2\x2\t\x3\x2\x2\x2\x2\v\x3\x2");
|
||||||
|
sb.Append("\x2\x2\x2\x11\x3\x2\x2\x2\x3\x13\x3\x2\x2\x2\x5\x16\x3\x2\x2");
|
||||||
|
sb.Append("\x2\a\x18\x3\x2\x2\x2\t\x1A\x3\x2\x2\x2\v\x1C\x3\x2\x2\x2\r");
|
||||||
|
sb.Append("\'\x3\x2\x2\x2\xF)\x3\x2\x2\x2\x11+\x3\x2\x2\x2\x13\x14\a\x31");
|
||||||
|
sb.Append("\x2\x2\x14\x15\a\x31\x2\x2\x15\x4\x3\x2\x2\x2\x16\x17\a\x31");
|
||||||
|
sb.Append("\x2\x2\x17\x6\x3\x2\x2\x2\x18\x19\a,\x2\x2\x19\b\x3\x2\x2\x2");
|
||||||
|
sb.Append("\x1A\x1B\a#\x2\x2\x1B\n\x3\x2\x2\x2\x1C \x5\xF\b\x2\x1D\x1F");
|
||||||
|
sb.Append("\x5\r\a\x2\x1E\x1D\x3\x2\x2\x2\x1F\"\x3\x2\x2\x2 \x1E\x3\x2");
|
||||||
|
sb.Append("\x2\x2 !\x3\x2\x2\x2!#\x3\x2\x2\x2\" \x3\x2\x2\x2#$\b\x6\x2");
|
||||||
|
sb.Append("\x2$\f\x3\x2\x2\x2%(\x5\xF\b\x2&(\t\x2\x2\x2\'%\x3\x2\x2\x2");
|
||||||
|
sb.Append("\'&\x3\x2\x2\x2(\xE\x3\x2\x2\x2)*\t\x3\x2\x2*\x10\x3\x2\x2\x2");
|
||||||
|
sb.Append("+/\a)\x2\x2,.\v\x2\x2\x2-,\x3\x2\x2\x2.\x31\x3\x2\x2\x2/\x30");
|
||||||
|
sb.Append("\x3\x2\x2\x2/-\x3\x2\x2\x2\x30\x32\x3\x2\x2\x2\x31/\x3\x2\x2");
|
||||||
|
sb.Append("\x2\x32\x33\a)\x2\x2\x33\x12\x3\x2\x2\x2\x6\x2 \'/\x3\x3\x6");
|
||||||
|
sb.Append("\x2");
|
||||||
|
return sb.ToString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static readonly ATN _ATN =
|
||||||
|
new ATNDeserializer().Deserialize(_serializedATN.ToCharArray());
|
||||||
|
|
||||||
public override void Action(RuleContext _localctx, int ruleIndex, int actionIndex) {
|
|
||||||
switch (ruleIndex) {
|
|
||||||
case 4 : ID_action(_localctx, actionIndex); break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private void ID_action(RuleContext _localctx, int actionIndex) {
|
|
||||||
switch (actionIndex) {
|
|
||||||
case 0:
|
|
||||||
String text = Text;
|
|
||||||
if ( Char.IsUpper(text[0]) )
|
|
||||||
Type = TokenRef;
|
|
||||||
else
|
|
||||||
Type = RuleRef;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static readonly string _serializedATN =
|
|
||||||
"\x3\x430\xD6D1\x8206\xAD2D\x4417\xAEF1\x8D80\xAADD\x2\n\x34\b\x1\x4\x2"+
|
|
||||||
"\t\x2\x4\x3\t\x3\x4\x4\t\x4\x4\x5\t\x5\x4\x6\t\x6\x4\a\t\a\x4\b\t\b\x4"+
|
|
||||||
"\t\t\t\x3\x2\x3\x2\x3\x2\x3\x3\x3\x3\x3\x4\x3\x4\x3\x5\x3\x5\x3\x6\x3"+
|
|
||||||
"\x6\a\x6\x1F\n\x6\f\x6\xE\x6\"\v\x6\x3\x6\x3\x6\x3\a\x3\a\x5\a(\n\a\x3"+
|
|
||||||
"\b\x3\b\x3\t\x3\t\a\t.\n\t\f\t\xE\t\x31\v\t\x3\t\x3\t\x3/\x2\n\x3\x5\x5"+
|
|
||||||
"\x6\a\a\t\b\v\t\r\x2\xF\x2\x11\n\x3\x2\x4\a\x2\x32;\x61\x61\xB9\xB9\x302"+
|
|
||||||
"\x371\x2041\x2042\xF\x2\x43\\\x63|\xC2\xD8\xDA\xF8\xFA\x301\x372\x37F"+
|
|
||||||
"\x381\x2001\x200E\x200F\x2072\x2191\x2C02\x2FF1\x3003\xD801\xF902\xFDD1"+
|
|
||||||
"\xFDF2\xFFFF\x34\x2\x3\x3\x2\x2\x2\x2\x5\x3\x2\x2\x2\x2\a\x3\x2\x2\x2"+
|
|
||||||
"\x2\t\x3\x2\x2\x2\x2\v\x3\x2\x2\x2\x2\x11\x3\x2\x2\x2\x3\x13\x3\x2\x2"+
|
|
||||||
"\x2\x5\x16\x3\x2\x2\x2\a\x18\x3\x2\x2\x2\t\x1A\x3\x2\x2\x2\v\x1C\x3\x2"+
|
|
||||||
"\x2\x2\r\'\x3\x2\x2\x2\xF)\x3\x2\x2\x2\x11+\x3\x2\x2\x2\x13\x14\a\x31"+
|
|
||||||
"\x2\x2\x14\x15\a\x31\x2\x2\x15\x4\x3\x2\x2\x2\x16\x17\a\x31\x2\x2\x17"+
|
|
||||||
"\x6\x3\x2\x2\x2\x18\x19\a,\x2\x2\x19\b\x3\x2\x2\x2\x1A\x1B\a#\x2\x2\x1B"+
|
|
||||||
"\n\x3\x2\x2\x2\x1C \x5\xF\b\x2\x1D\x1F\x5\r\a\x2\x1E\x1D\x3\x2\x2\x2\x1F"+
|
|
||||||
"\"\x3\x2\x2\x2 \x1E\x3\x2\x2\x2 !\x3\x2\x2\x2!#\x3\x2\x2\x2\" \x3\x2\x2"+
|
|
||||||
"\x2#$\b\x6\x2\x2$\f\x3\x2\x2\x2%(\x5\xF\b\x2&(\t\x2\x2\x2\'%\x3\x2\x2"+
|
|
||||||
"\x2\'&\x3\x2\x2\x2(\xE\x3\x2\x2\x2)*\t\x3\x2\x2*\x10\x3\x2\x2\x2+/\a)"+
|
|
||||||
"\x2\x2,.\v\x2\x2\x2-,\x3\x2\x2\x2.\x31\x3\x2\x2\x2/\x30\x3\x2\x2\x2/-"+
|
|
||||||
"\x3\x2\x2\x2\x30\x32\x3\x2\x2\x2\x31/\x3\x2\x2\x2\x32\x33\a)\x2\x2\x33"+
|
|
||||||
"\x12\x3\x2\x2\x2\x6\x2 \'/\x3\x3\x6\x2";
|
|
||||||
public static readonly ATN _ATN =
|
|
||||||
new ATNDeserializer().Deserialize(_serializedATN.ToCharArray());
|
|
||||||
}
|
}
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue