Next overhaul (more TODOs fixed)

- Added an even simpler grammar to ease debugging while getting the lib into a working state.
- Added helper template is<> to ease frequent type checks (for value types, ref types and shared_ptr). Added some unit tests for that as well.
- Changed the MurmurHash::hashCode() function to take shared_ptr as this is the only variant we need. Had to change the MurmurHash unit tests for that.
- Removed conflicting IntStream::_EOF (and other variants). We use the C runtime EOF value instead.
- Changed all references to semantic contexts, prediction context and the prediction context cache to use shared_ptr<>. Created *Ref typedefs to simplify usage.
- Adjusted the C++ string templates for that.
- Fixed a number of memory leaks + some cleanup.
This commit is contained in:
Mike Lischke 2016-04-06 15:07:25 +02:00
parent 1ca5b38868
commit d1b59ca5af
130 changed files with 1323 additions and 3663 deletions

View File

@ -12,11 +12,15 @@
#include "TLexer.h" #include "TLexer.h"
#include "TParser.h" #include "TParser.h"
#include "TestLexer.h"
#include "TestParser.h"
using namespace antlrcpptest; using namespace antlrcpptest;
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
int main(int argc, const char * argv[]) { int main(int argc, const char * argv[]) {
/*
ANTLRInputStream input(L"<foo><conquer>"); ANTLRInputStream input(L"<foo><conquer>");
TLexer lexer(&input); TLexer lexer(&input);
CommonTokenStream tokens(&lexer); CommonTokenStream tokens(&lexer);
@ -24,6 +28,15 @@ int main(int argc, const char * argv[]) {
TParser parser(&tokens); TParser parser(&tokens);
std::shared_ptr<tree::ParseTree> tree = parser.main(); std::shared_ptr<tree::ParseTree> tree = parser.main();
std::wcout << tree->toStringTree(&parser); std::wcout << tree->toStringTree(&parser);
*/
ANTLRInputStream input(L"ab");
TestLexer lexer(&input);
CommonTokenStream tokens(&lexer);
TestParser parser(&tokens);
std::shared_ptr<tree::ParseTree> tree = parser.main();
std::wcout << tree->toStringTree(&parser);
return 0; return 0;
} }

View File

@ -56,39 +56,39 @@ using namespace org::antlr::v4::runtime::misc;
- (void)testANTLRInputStreamCreation { - (void)testANTLRInputStreamCreation {
ANTLRInputStream stream1; ANTLRInputStream stream1;
XCTAssert(stream1.toString().empty()); XCTAssert(stream1.toString().empty());
XCTAssertEqual(stream1.index(), (size_t)0); XCTAssertEqual(stream1.index(), 0U);
ANTLRInputStream stream2(L"To be or not to be"); ANTLRInputStream stream2(L"To be or not to be");
XCTAssert(stream2.toString() == L"To be or not to be"); XCTAssert(stream2.toString() == L"To be or not to be");
XCTAssertEqual(stream2.index(), (size_t)0); XCTAssertEqual(stream2.index(), 0U);
XCTAssertEqual(stream2.size(), (size_t)18); XCTAssertEqual(stream2.size(), 18U);
wchar_t data[] = L"Lorem ipsum dolor sit amet"; wchar_t data[] = L"Lorem ipsum dolor sit amet";
ANTLRInputStream stream3(data, sizeof(data) / sizeof(data[0])); ANTLRInputStream stream3(data, sizeof(data) / sizeof(data[0]));
XCTAssert(stream3.toString() == std::wstring(L"Lorem ipsum dolor sit amet\0", 27)); XCTAssert(stream3.toString() == std::wstring(L"Lorem ipsum dolor sit amet\0", 27));
XCTAssertEqual(stream3.index(), (size_t)0); XCTAssertEqual(stream3.index(), 0U);
XCTAssertEqual(stream3.size(), (size_t)27); XCTAssertEqual(stream3.size(), 27U);
std::wstringstream input(data, sizeof(data) / sizeof(data[0])); std::wstringstream input(data, sizeof(data) / sizeof(data[0]));
ANTLRInputStream stream4(input); ANTLRInputStream stream4(input);
XCTAssertEqual(stream4.index(), (size_t)0); XCTAssertEqual(stream4.index(), 0U);
XCTAssertEqual(stream4.size(), (size_t)26); XCTAssertEqual(stream4.size(), 26U);
std::wstring longString(33333, L'a'); std::wstring longString(33333, L'a');
input.str(longString); input.str(longString);
stream4.load(input, 0); stream4.load(input, 0);
XCTAssertEqual(stream4.index(), (size_t)0); XCTAssertEqual(stream4.index(), 0U);
XCTAssertEqual(stream4.size(), (size_t)26); // Nothing changed as the stream is still at eof. XCTAssertEqual(stream4.size(), 26U); // Nothing changed as the stream is still at eof.
input.clear(); input.clear();
stream4.load(input, 0); stream4.load(input, 0);
XCTAssertEqual(stream4.size(), (size_t)33333); XCTAssertEqual(stream4.size(), 33333U);
} }
- (void)testANTLRInputStreamUse { - (void)testANTLRInputStreamUse {
std::wstring text(L"🚧Lorem ipsum dolor sit amet🕶"); std::wstring text(L"🚧Lorem ipsum dolor sit amet🕶");
ANTLRInputStream stream(text); ANTLRInputStream stream(text);
XCTAssertEqual(stream.index(), (size_t)0); XCTAssertEqual(stream.index(), 0U);
XCTAssertEqual(stream.size(), text.size()); XCTAssertEqual(stream.size(), text.size());
for (size_t i = 0; i < stream.size(); ++i) { for (size_t i = 0; i < stream.size(); ++i) {
@ -106,13 +106,13 @@ using namespace org::antlr::v4::runtime::misc;
XCTAssertEqual(stream.index(), text.size()); XCTAssertEqual(stream.index(), text.size());
stream.reset(); stream.reset();
XCTAssertEqual(stream.index(), (size_t)0); XCTAssertEqual(stream.index(), 0U);
XCTAssertEqual(stream.LA(0), (size_t)0); XCTAssertEqual(stream.LA(0), 0);
for (size_t i = 1; i < text.size(); ++i) { for (size_t i = 1; i < text.size(); ++i) {
XCTAssertEqual(stream.LA((int)i), (size_t)text[i - 1]); // LA(1) means: current char. XCTAssertEqual(stream.LA((ssize_t)i), text[i - 1]); // LA(1) means: current char.
XCTAssertEqual(stream.LT((int)i), (size_t)text[i - 1]); // LT is mapped to LA. XCTAssertEqual(stream.LT((ssize_t)i), text[i - 1]); // LT is mapped to LA.
XCTAssertEqual(stream.index(), (size_t)0); // No consumption when looking ahead. XCTAssertEqual(stream.index(), 0U); // No consumption when looking ahead.
} }
stream.seek(text.size() - 1); stream.seek(text.size() - 1);
@ -123,24 +123,24 @@ using namespace org::antlr::v4::runtime::misc;
stream.seek(text.size() - 1); stream.seek(text.size() - 1);
for (size_t i = 1; i < text.size() - 1; ++i) { for (size_t i = 1; i < text.size() - 1; ++i) {
XCTAssertEqual(stream.LA((ssize_t)-i), (size_t)text[text.size() - i - 1]); // LA(-1) means: previous char. XCTAssertEqual(stream.LA((ssize_t)-i), text[text.size() - i - 1]); // LA(-1) means: previous char.
XCTAssertEqual(stream.LT((ssize_t)-i), (size_t)text[text.size() - i - 1]); // LT is mapped to LA. XCTAssertEqual(stream.LT((ssize_t)-i), text[text.size() - i - 1]); // LT is mapped to LA.
XCTAssertEqual(stream.index(), text.size() - 1); // No consumption when looking ahead. XCTAssertEqual(stream.index(), text.size() - 1); // No consumption when looking ahead.
} }
XCTAssertEqual((int)stream.LA(-10000), IntStream::_EOF); XCTAssertEqual((int)stream.LA(-10000), EOF);
// Mark and release do nothing. // Mark and release do nothing.
stream.reset(); stream.reset();
XCTAssertEqual(stream.index(), (size_t)0); XCTAssertEqual(stream.index(), 0U);
ssize_t marker = stream.mark(); ssize_t marker = stream.mark();
XCTAssertEqual(marker, -1); XCTAssertEqual(marker, -1);
stream.seek(10); stream.seek(10);
XCTAssertEqual(stream.index(), (size_t)10); XCTAssertEqual(stream.index(), 10U);
XCTAssertEqual(stream.mark(), -1); XCTAssertEqual(stream.mark(), -1);
stream.release(marker); stream.release(marker);
XCTAssertEqual(stream.index(), (size_t)10); XCTAssertEqual(stream.index(), 10U);
misc::Interval interval1(2, 10); // From - to, inclusive. misc::Interval interval1(2, 10); // From - to, inclusive.
std::wstring output = stream.getText(interval1); std::wstring output = stream.getText(interval1);

View File

@ -35,9 +35,11 @@
#include "Token.h" #include "Token.h"
#include "Exceptions.h" #include "Exceptions.h"
#include "Lexer.h" #include "Lexer.h"
#include "CPPUtils.h"
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
using namespace org::antlr::v4::runtime::misc; using namespace org::antlr::v4::runtime::misc;
using namespace antlrcpp;
@interface MiscClassTests : XCTestCase @interface MiscClassTests : XCTestCase
@ -55,39 +57,91 @@ using namespace org::antlr::v4::runtime::misc;
[super tearDown]; [super tearDown];
} }
- (void)testMurmurHash { - (void)testCPPUtils {
XCTAssertEqual(MurmurHash::initialize(), (size_t)0);
XCTAssertEqual(MurmurHash::initialize(31), (size_t)31);
XCTAssertEqual(MurmurHash::hashCode<size_t>({}, 0, 0), (size_t)0); class A { public: virtual ~A() {}; };
class B : public A { public: virtual ~B() {}; };
class C : public A { public: virtual ~C() {}; };
class D : public C { public: virtual ~D() {}; };
{
A a; B b; C c; D d;
XCTAssert(is<A>(b));
XCTAssertFalse(is<B>(a));
XCTAssert(is<A>(c));
XCTAssertFalse(is<B>(c));
XCTAssert(is<A>(d));
XCTAssert(is<C>(d));
XCTAssertFalse(is<B>(d));
}
{
A *a = new A(); B *b = new B(); C *c = new C(); D *d = new D();
XCTAssert(is<A*>(b));
XCTAssertFalse(is<B*>(a));
XCTAssert(is<A*>(c));
XCTAssertFalse(is<B*>(c));
XCTAssert(is<A*>(d));
XCTAssert(is<C*>(d));
XCTAssertFalse(is<B*>(d));
delete a; delete b; delete c; delete d;
}
{
std::shared_ptr<A> a(new A());
std::shared_ptr<B> b(new B());
std::shared_ptr<C> c(new C());
std::shared_ptr<D> d(new D());
XCTAssert(is<A>(b));
XCTAssertFalse(is<B>(a));
XCTAssert(is<A>(c));
XCTAssertFalse(is<B>(c));
XCTAssert(is<A>(d));
XCTAssert(is<C>(d));
XCTAssertFalse(is<B>(d));
}
}
- (void)testMurmurHash {
XCTAssertEqual(MurmurHash::initialize(), 0U);
XCTAssertEqual(MurmurHash::initialize(31), 31U);
XCTAssertEqual(MurmurHash::hashCode<size_t>({}, 0), 0U);
// In absence of real test vectors (64bit) for murmurhash I instead check if I can find duplicate hash values // In absence of real test vectors (64bit) for murmurhash I instead check if I can find duplicate hash values
// in a deterministic and a random sequence of 100K values each. // in a deterministic and a random sequence of 100K values each.
std::set<size_t> hashs; std::set<size_t> hashs;
for (size_t i = 0; i < 100000; ++i) { for (size_t i = 0; i < 100000; ++i) {
size_t data[] = { i, (size_t)(i * M_PI), arc4random()}; std::vector<size_t> data = { i, (size_t)(i * M_PI), arc4random()};
size_t hash = MurmurHash::hashCode(data, 3, 0); size_t hash = 0;
for (auto value : data)
hash = MurmurHash::update(hash, value);
hash = MurmurHash::finish(hash, data.size());
hashs.insert(hash); hashs.insert(hash);
} }
XCTAssertEqual(hashs.size(), (size_t)100000, @"At least one duplicat hash found."); XCTAssertEqual(hashs.size(), 100000U, @"At least one duplicat hash found.");
hashs.clear(); hashs.clear();
for (size_t i = 0; i < 100000; ++i) { for (size_t i = 0; i < 100000; ++i) {
size_t data[] = { i, (size_t)(i * M_PI)}; std::vector<size_t> data = { i, (size_t)(i * M_PI)};
size_t hash = MurmurHash::hashCode(data, 2, 0); size_t hash = 0;
for (auto value : data)
hash = MurmurHash::update(hash, value);
hash = MurmurHash::finish(hash, data.size());
hashs.insert(hash); hashs.insert(hash);
} }
XCTAssertEqual(hashs.size(), (size_t)100000, @"At least one duplicat hash found."); XCTAssertEqual(hashs.size(), 100000U, @"At least one duplicat hash found.");
// Another test with fixed input but varying seeds. // Another test with fixed input but varying seeds.
// Note: the higher the seed the less LSDs are in the result (for small input data). // Note: the higher the seed the less LSDs are in the result (for small input data).
hashs.clear(); hashs.clear();
std::vector<size_t> data = { L'µ', 'a', '@', '1' };
for (size_t i = 0; i < 100000; ++i) { for (size_t i = 0; i < 100000; ++i) {
size_t data[] = { L'µ', 'a', '@', '1' }; size_t hash = i;
size_t hash = MurmurHash::hashCode(data, 4, i); for (auto value : data)
hash = MurmurHash::update(hash, value);
hash = MurmurHash::finish(hash, data.size());
hashs.insert(hash); hashs.insert(hash);
} }
XCTAssertEqual(hashs.size(), (size_t)100000, @"At least one duplicat hash found."); XCTAssertEqual(hashs.size(), 100000U, @"At least one duplicat hash found.");
} }
- (void)testInterval { - (void)testInterval {
@ -104,9 +158,9 @@ using namespace org::antlr::v4::runtime::misc;
XCTAssert(Interval(0, 0) == Interval(0, 0)); XCTAssert(Interval(0, 0) == Interval(0, 0));
XCTAssertFalse(Interval(0, 1) == Interval(1, 2)); XCTAssertFalse(Interval(0, 1) == Interval(1, 2));
XCTAssertEqual(Interval().hashCode(), (size_t)22070); XCTAssertEqual(Interval().hashCode(), 22070U);
XCTAssertEqual(Interval(0, 0).hashCode(), (size_t)22103); XCTAssertEqual(Interval(0, 0).hashCode(), 22103U);
XCTAssertEqual(Interval(10, 2000).hashCode(), (size_t)24413); XCTAssertEqual(Interval(10, 2000).hashCode(), 24413U);
// Results for the interval test functions in this order: // Results for the interval test functions in this order:
// startsBeforeDisjoint // startsBeforeDisjoint
@ -292,7 +346,7 @@ using namespace org::antlr::v4::runtime::misc;
set4.clear(); set4.clear();
XCTFail(@"Expected exception"); XCTFail(@"Expected exception");
} }
catch ( IllegalStateException *e) { catch (IllegalStateException &e) {
} }
set4.setReadOnly(false); set4.setReadOnly(false);

View File

@ -19,6 +19,8 @@
276927251C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */ = {isa = PBXBuildFile; fileRef = 276927231C9ED49100E4EBF8 /* antlrcpp-Prefix.h */; }; 276927251C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */ = {isa = PBXBuildFile; fileRef = 276927231C9ED49100E4EBF8 /* antlrcpp-Prefix.h */; };
278A66FB1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */; }; 278A66FB1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */; };
278A66FC1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */; }; 278A66FC1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */; };
27BC755D1CB41B0D00AE780B /* TestLexer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27BC75591CB41B0D00AE780B /* TestLexer.cpp */; };
27BC755E1CB41B0D00AE780B /* TestParser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27BC755B1CB41B0D00AE780B /* TestParser.cpp */; };
27C666AC1C9584050021E494 /* ANTLRErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6665D1C9584050021E494 /* ANTLRErrorListener.h */; }; 27C666AC1C9584050021E494 /* ANTLRErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6665D1C9584050021E494 /* ANTLRErrorListener.h */; };
27C666AD1C9584050021E494 /* ANTLRErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6665D1C9584050021E494 /* ANTLRErrorListener.h */; }; 27C666AD1C9584050021E494 /* ANTLRErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6665D1C9584050021E494 /* ANTLRErrorListener.h */; };
27C666AE1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6665E1C9584050021E494 /* ANTLRErrorStrategy.cpp */; }; 27C666AE1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6665E1C9584050021E494 /* ANTLRErrorStrategy.cpp */; };
@ -299,10 +301,6 @@
27C668251C95846E0021E494 /* PredictionContext.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C667861C95846E0021E494 /* PredictionContext.cpp */; }; 27C668251C95846E0021E494 /* PredictionContext.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C667861C95846E0021E494 /* PredictionContext.cpp */; };
27C668261C95846E0021E494 /* PredictionContext.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667871C95846E0021E494 /* PredictionContext.h */; }; 27C668261C95846E0021E494 /* PredictionContext.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667871C95846E0021E494 /* PredictionContext.h */; };
27C668271C95846E0021E494 /* PredictionContext.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667871C95846E0021E494 /* PredictionContext.h */; }; 27C668271C95846E0021E494 /* PredictionContext.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667871C95846E0021E494 /* PredictionContext.h */; };
27C668281C95846E0021E494 /* PredictionContextCache.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C667881C95846E0021E494 /* PredictionContextCache.cpp */; };
27C668291C95846E0021E494 /* PredictionContextCache.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C667881C95846E0021E494 /* PredictionContextCache.cpp */; };
27C6682A1C95846E0021E494 /* PredictionContextCache.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667891C95846E0021E494 /* PredictionContextCache.h */; };
27C6682B1C95846E0021E494 /* PredictionContextCache.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C667891C95846E0021E494 /* PredictionContextCache.h */; };
27C6682C1C95846E0021E494 /* PredictionMode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6678A1C95846E0021E494 /* PredictionMode.cpp */; }; 27C6682C1C95846E0021E494 /* PredictionMode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6678A1C95846E0021E494 /* PredictionMode.cpp */; };
27C6682D1C95846E0021E494 /* PredictionMode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6678A1C95846E0021E494 /* PredictionMode.cpp */; }; 27C6682D1C95846E0021E494 /* PredictionMode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6678A1C95846E0021E494 /* PredictionMode.cpp */; };
27C6682E1C95846E0021E494 /* PredictionMode.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6678B1C95846E0021E494 /* PredictionMode.h */; }; 27C6682E1C95846E0021E494 /* PredictionMode.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6678B1C95846E0021E494 /* PredictionMode.h */; };
@ -375,8 +373,6 @@
27C6687A1C9584B60021E494 /* LexerDFASerializer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6686B1C9584B60021E494 /* LexerDFASerializer.cpp */; }; 27C6687A1C9584B60021E494 /* LexerDFASerializer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6686B1C9584B60021E494 /* LexerDFASerializer.cpp */; };
27C6687B1C9584B60021E494 /* LexerDFASerializer.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6686C1C9584B60021E494 /* LexerDFASerializer.h */; }; 27C6687B1C9584B60021E494 /* LexerDFASerializer.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6686C1C9584B60021E494 /* LexerDFASerializer.h */; };
27C6687C1C9584B60021E494 /* LexerDFASerializer.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6686C1C9584B60021E494 /* LexerDFASerializer.h */; }; 27C6687C1C9584B60021E494 /* LexerDFASerializer.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6686C1C9584B60021E494 /* LexerDFASerializer.h */; };
27C668A81C9584FA0021E494 /* DoubleKeyMap.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668821C9584FA0021E494 /* DoubleKeyMap.h */; };
27C668A91C9584FA0021E494 /* DoubleKeyMap.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668821C9584FA0021E494 /* DoubleKeyMap.h */; };
27C668AA1C9584FA0021E494 /* EqualityComparator.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668841C9584FA0021E494 /* EqualityComparator.cpp */; }; 27C668AA1C9584FA0021E494 /* EqualityComparator.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668841C9584FA0021E494 /* EqualityComparator.cpp */; };
27C668AB1C9584FA0021E494 /* EqualityComparator.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668841C9584FA0021E494 /* EqualityComparator.cpp */; }; 27C668AB1C9584FA0021E494 /* EqualityComparator.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668841C9584FA0021E494 /* EqualityComparator.cpp */; };
27C668AC1C9584FA0021E494 /* EqualityComparator.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668851C9584FA0021E494 /* EqualityComparator.h */; }; 27C668AC1C9584FA0021E494 /* EqualityComparator.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668851C9584FA0021E494 /* EqualityComparator.h */; };
@ -389,26 +385,10 @@
27C668B71C9584FA0021E494 /* IntervalSet.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6688A1C9584FA0021E494 /* IntervalSet.cpp */; }; 27C668B71C9584FA0021E494 /* IntervalSet.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6688A1C9584FA0021E494 /* IntervalSet.cpp */; };
27C668B81C9584FA0021E494 /* IntervalSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6688B1C9584FA0021E494 /* IntervalSet.h */; }; 27C668B81C9584FA0021E494 /* IntervalSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6688B1C9584FA0021E494 /* IntervalSet.h */; };
27C668B91C9584FA0021E494 /* IntervalSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6688B1C9584FA0021E494 /* IntervalSet.h */; }; 27C668B91C9584FA0021E494 /* IntervalSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6688B1C9584FA0021E494 /* IntervalSet.h */; };
27C668C21C9584FA0021E494 /* LogManager.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668901C9584FA0021E494 /* LogManager.cpp */; };
27C668C31C9584FA0021E494 /* LogManager.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668901C9584FA0021E494 /* LogManager.cpp */; };
27C668C41C9584FA0021E494 /* LogManager.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668911C9584FA0021E494 /* LogManager.h */; };
27C668C51C9584FA0021E494 /* LogManager.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668911C9584FA0021E494 /* LogManager.h */; };
27C668C61C9584FA0021E494 /* MultiMap.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668921C9584FA0021E494 /* MultiMap.cpp */; };
27C668C71C9584FA0021E494 /* MultiMap.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668921C9584FA0021E494 /* MultiMap.cpp */; };
27C668C81C9584FA0021E494 /* MultiMap.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668931C9584FA0021E494 /* MultiMap.h */; };
27C668C91C9584FA0021E494 /* MultiMap.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668931C9584FA0021E494 /* MultiMap.h */; };
27C668CA1C9584FA0021E494 /* MurmurHash.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668941C9584FA0021E494 /* MurmurHash.cpp */; }; 27C668CA1C9584FA0021E494 /* MurmurHash.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668941C9584FA0021E494 /* MurmurHash.cpp */; };
27C668CB1C9584FA0021E494 /* MurmurHash.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668941C9584FA0021E494 /* MurmurHash.cpp */; }; 27C668CB1C9584FA0021E494 /* MurmurHash.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C668941C9584FA0021E494 /* MurmurHash.cpp */; };
27C668CC1C9584FA0021E494 /* MurmurHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668951C9584FA0021E494 /* MurmurHash.h */; }; 27C668CC1C9584FA0021E494 /* MurmurHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668951C9584FA0021E494 /* MurmurHash.h */; };
27C668CD1C9584FA0021E494 /* MurmurHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668951C9584FA0021E494 /* MurmurHash.h */; }; 27C668CD1C9584FA0021E494 /* MurmurHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C668951C9584FA0021E494 /* MurmurHash.h */; };
27C668D61C9584FA0021E494 /* OrderedHashSet.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689A1C9584FA0021E494 /* OrderedHashSet.cpp */; };
27C668D71C9584FA0021E494 /* OrderedHashSet.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689A1C9584FA0021E494 /* OrderedHashSet.cpp */; };
27C668D81C9584FA0021E494 /* OrderedHashSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689B1C9584FA0021E494 /* OrderedHashSet.h */; };
27C668D91C9584FA0021E494 /* OrderedHashSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689B1C9584FA0021E494 /* OrderedHashSet.h */; };
27C668DA1C9584FA0021E494 /* ParseCancellationException.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689C1C9584FA0021E494 /* ParseCancellationException.cpp */; };
27C668DB1C9584FA0021E494 /* ParseCancellationException.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689C1C9584FA0021E494 /* ParseCancellationException.cpp */; };
27C668DC1C9584FA0021E494 /* ParseCancellationException.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689D1C9584FA0021E494 /* ParseCancellationException.h */; };
27C668DD1C9584FA0021E494 /* ParseCancellationException.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689D1C9584FA0021E494 /* ParseCancellationException.h */; };
27C668DE1C9584FA0021E494 /* TestRig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689E1C9584FA0021E494 /* TestRig.cpp */; }; 27C668DE1C9584FA0021E494 /* TestRig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689E1C9584FA0021E494 /* TestRig.cpp */; };
27C668DF1C9584FA0021E494 /* TestRig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689E1C9584FA0021E494 /* TestRig.cpp */; }; 27C668DF1C9584FA0021E494 /* TestRig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6689E1C9584FA0021E494 /* TestRig.cpp */; };
27C668E01C9584FA0021E494 /* TestRig.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689F1C9584FA0021E494 /* TestRig.h */; }; 27C668E01C9584FA0021E494 /* TestRig.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C6689F1C9584FA0021E494 /* TestRig.h */; };
@ -527,42 +507,6 @@
27C66A1D1C958AB30021E494 /* TextChunk.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FE1C958AB30021E494 /* TextChunk.h */; }; 27C66A1D1C958AB30021E494 /* TextChunk.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FE1C958AB30021E494 /* TextChunk.h */; };
27C66A1E1C958AB30021E494 /* TokenTagToken.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FF1C958AB30021E494 /* TokenTagToken.h */; }; 27C66A1E1C958AB30021E494 /* TokenTagToken.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FF1C958AB30021E494 /* TokenTagToken.h */; };
27C66A1F1C958AB30021E494 /* TokenTagToken.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FF1C958AB30021E494 /* TokenTagToken.h */; }; 27C66A1F1C958AB30021E494 /* TokenTagToken.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C669FF1C958AB30021E494 /* TokenTagToken.h */; };
27C66A341C958AC10021E494 /* XPath.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A201C958AC10021E494 /* XPath.cpp */; };
27C66A351C958AC10021E494 /* XPath.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A201C958AC10021E494 /* XPath.cpp */; };
27C66A361C958AC10021E494 /* XPathElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A211C958AC10021E494 /* XPathElement.cpp */; };
27C66A371C958AC10021E494 /* XPathElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A211C958AC10021E494 /* XPathElement.cpp */; };
27C66A3A1C958AC10021E494 /* XPathLexerErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A231C958AC10021E494 /* XPathLexerErrorListener.cpp */; };
27C66A3B1C958AC10021E494 /* XPathLexerErrorListener.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A231C958AC10021E494 /* XPathLexerErrorListener.cpp */; };
27C66A3C1C958AC10021E494 /* XPathRuleAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A241C958AC10021E494 /* XPathRuleAnywhereElement.cpp */; };
27C66A3D1C958AC10021E494 /* XPathRuleAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A241C958AC10021E494 /* XPathRuleAnywhereElement.cpp */; };
27C66A3E1C958AC10021E494 /* XPathRuleElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A251C958AC10021E494 /* XPathRuleElement.cpp */; };
27C66A3F1C958AC10021E494 /* XPathRuleElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A251C958AC10021E494 /* XPathRuleElement.cpp */; };
27C66A401C958AC10021E494 /* XPathTokenAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A261C958AC10021E494 /* XPathTokenAnywhereElement.cpp */; };
27C66A411C958AC10021E494 /* XPathTokenAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A261C958AC10021E494 /* XPathTokenAnywhereElement.cpp */; };
27C66A421C958AC10021E494 /* XPathTokenElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A271C958AC10021E494 /* XPathTokenElement.cpp */; };
27C66A431C958AC10021E494 /* XPathTokenElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A271C958AC10021E494 /* XPathTokenElement.cpp */; };
27C66A441C958AC10021E494 /* XPathWildcardAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A281C958AC10021E494 /* XPathWildcardAnywhereElement.cpp */; };
27C66A451C958AC10021E494 /* XPathWildcardAnywhereElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A281C958AC10021E494 /* XPathWildcardAnywhereElement.cpp */; };
27C66A461C958AC10021E494 /* XPathWildcardElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A291C958AC10021E494 /* XPathWildcardElement.cpp */; };
27C66A471C958AC10021E494 /* XPathWildcardElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A291C958AC10021E494 /* XPathWildcardElement.cpp */; };
27C66A481C958AC10021E494 /* XPath.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2A1C958AC10021E494 /* XPath.h */; };
27C66A491C958AC10021E494 /* XPath.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2A1C958AC10021E494 /* XPath.h */; };
27C66A4A1C958AC10021E494 /* XPathElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2B1C958AC10021E494 /* XPathElement.h */; };
27C66A4B1C958AC10021E494 /* XPathElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2B1C958AC10021E494 /* XPathElement.h */; };
27C66A4E1C958AC10021E494 /* XPathLexerErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2D1C958AC10021E494 /* XPathLexerErrorListener.h */; };
27C66A4F1C958AC10021E494 /* XPathLexerErrorListener.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2D1C958AC10021E494 /* XPathLexerErrorListener.h */; };
27C66A501C958AC10021E494 /* XPathRuleAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2E1C958AC10021E494 /* XPathRuleAnywhereElement.h */; };
27C66A511C958AC10021E494 /* XPathRuleAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2E1C958AC10021E494 /* XPathRuleAnywhereElement.h */; };
27C66A521C958AC10021E494 /* XPathRuleElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2F1C958AC10021E494 /* XPathRuleElement.h */; };
27C66A531C958AC10021E494 /* XPathRuleElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A2F1C958AC10021E494 /* XPathRuleElement.h */; };
27C66A541C958AC10021E494 /* XPathTokenAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A301C958AC10021E494 /* XPathTokenAnywhereElement.h */; };
27C66A551C958AC10021E494 /* XPathTokenAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A301C958AC10021E494 /* XPathTokenAnywhereElement.h */; };
27C66A561C958AC10021E494 /* XPathTokenElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A311C958AC10021E494 /* XPathTokenElement.h */; };
27C66A571C958AC10021E494 /* XPathTokenElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A311C958AC10021E494 /* XPathTokenElement.h */; };
27C66A581C958AC10021E494 /* XPathWildcardAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A321C958AC10021E494 /* XPathWildcardAnywhereElement.h */; };
27C66A591C958AC10021E494 /* XPathWildcardAnywhereElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A321C958AC10021E494 /* XPathWildcardAnywhereElement.h */; };
27C66A5A1C958AC10021E494 /* XPathWildcardElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A331C958AC10021E494 /* XPathWildcardElement.h */; };
27C66A5B1C958AC10021E494 /* XPathWildcardElement.h in Headers */ = {isa = PBXBuildFile; fileRef = 27C66A331C958AC10021E494 /* XPathWildcardElement.h */; };
27C66A6A1C9591280021E494 /* main.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A691C9591280021E494 /* main.cpp */; }; 27C66A6A1C9591280021E494 /* main.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C66A691C9591280021E494 /* main.cpp */; };
27C66A701C9591550021E494 /* antlrcpp.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 37D727AA1867AF1E007B6D10 /* antlrcpp.dylib */; }; 27C66A701C9591550021E494 /* antlrcpp.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 37D727AA1867AF1E007B6D10 /* antlrcpp.dylib */; };
27C6E17F1C972FFC0079AF06 /* TLexer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6E1711C972FFB0079AF06 /* TLexer.cpp */; }; 27C6E17F1C972FFC0079AF06 /* TLexer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 27C6E1711C972FFB0079AF06 /* TLexer.cpp */; };
@ -611,6 +555,10 @@
274FC6D81CA96B6C008D4374 /* MiscClassTests.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = MiscClassTests.mm; sourceTree = "<group>"; wrapsLines = 0; }; 274FC6D81CA96B6C008D4374 /* MiscClassTests.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = MiscClassTests.mm; sourceTree = "<group>"; wrapsLines = 0; };
276927231C9ED49100E4EBF8 /* antlrcpp-Prefix.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; name = "antlrcpp-Prefix.h"; path = "../../runtime/antlrcpp-Prefix.h"; sourceTree = "<group>"; }; 276927231C9ED49100E4EBF8 /* antlrcpp-Prefix.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; name = "antlrcpp-Prefix.h"; path = "../../runtime/antlrcpp-Prefix.h"; sourceTree = "<group>"; };
278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ANTLRErrorListener.cpp; path = ../../runtime/ANTLRErrorListener.cpp; sourceTree = SOURCE_ROOT; }; 278A66FA1C95838E002D667E /* ANTLRErrorListener.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ANTLRErrorListener.cpp; path = ../../runtime/ANTLRErrorListener.cpp; sourceTree = SOURCE_ROOT; };
27BC75591CB41B0D00AE780B /* TestLexer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TestLexer.cpp; path = ../generated/TestLexer.cpp; sourceTree = "<group>"; };
27BC755A1CB41B0D00AE780B /* TestLexer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TestLexer.h; path = ../generated/TestLexer.h; sourceTree = "<group>"; };
27BC755B1CB41B0D00AE780B /* TestParser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TestParser.cpp; path = ../generated/TestParser.cpp; sourceTree = "<group>"; };
27BC755C1CB41B0D00AE780B /* TestParser.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TestParser.h; path = ../generated/TestParser.h; sourceTree = "<group>"; };
27C6665D1C9584050021E494 /* ANTLRErrorListener.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ANTLRErrorListener.h; path = ../../runtime/ANTLRErrorListener.h; sourceTree = SOURCE_ROOT; wrapsLines = 0; }; 27C6665D1C9584050021E494 /* ANTLRErrorListener.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ANTLRErrorListener.h; path = ../../runtime/ANTLRErrorListener.h; sourceTree = SOURCE_ROOT; wrapsLines = 0; };
27C6665E1C9584050021E494 /* ANTLRErrorStrategy.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ANTLRErrorStrategy.cpp; path = ../../runtime/ANTLRErrorStrategy.cpp; sourceTree = SOURCE_ROOT; }; 27C6665E1C9584050021E494 /* ANTLRErrorStrategy.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ANTLRErrorStrategy.cpp; path = ../../runtime/ANTLRErrorStrategy.cpp; sourceTree = SOURCE_ROOT; };
27C6665F1C9584050021E494 /* ANTLRErrorStrategy.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ANTLRErrorStrategy.h; path = ../../runtime/ANTLRErrorStrategy.h; sourceTree = SOURCE_ROOT; }; 27C6665F1C9584050021E494 /* ANTLRErrorStrategy.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ANTLRErrorStrategy.h; path = ../../runtime/ANTLRErrorStrategy.h; sourceTree = SOURCE_ROOT; };
@ -673,7 +621,7 @@
27C666991C9584050021E494 /* Recognizer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Recognizer.cpp; path = ../../runtime/Recognizer.cpp; sourceTree = SOURCE_ROOT; }; 27C666991C9584050021E494 /* Recognizer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Recognizer.cpp; path = ../../runtime/Recognizer.cpp; sourceTree = SOURCE_ROOT; };
27C6669A1C9584050021E494 /* RuleContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = RuleContext.cpp; path = ../../runtime/RuleContext.cpp; sourceTree = SOURCE_ROOT; wrapsLines = 0; }; 27C6669A1C9584050021E494 /* RuleContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = RuleContext.cpp; path = ../../runtime/RuleContext.cpp; sourceTree = SOURCE_ROOT; wrapsLines = 0; };
27C6669B1C9584050021E494 /* RuleContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RuleContext.h; path = ../../runtime/RuleContext.h; sourceTree = SOURCE_ROOT; }; 27C6669B1C9584050021E494 /* RuleContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RuleContext.h; path = ../../runtime/RuleContext.h; sourceTree = SOURCE_ROOT; };
27C6669C1C9584050021E494 /* Token.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Token.cpp; path = ../../runtime/Token.cpp; sourceTree = SOURCE_ROOT; }; 27C6669C1C9584050021E494 /* Token.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Token.cpp; path = ../../runtime/Token.cpp; sourceTree = SOURCE_ROOT; wrapsLines = 0; };
27C6669D1C9584050021E494 /* Token.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Token.h; path = ../../runtime/Token.h; sourceTree = SOURCE_ROOT; }; 27C6669D1C9584050021E494 /* Token.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Token.h; path = ../../runtime/Token.h; sourceTree = SOURCE_ROOT; };
27C6669E1C9584050021E494 /* TokenFactory.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TokenFactory.cpp; path = ../../runtime/TokenFactory.cpp; sourceTree = SOURCE_ROOT; }; 27C6669E1C9584050021E494 /* TokenFactory.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TokenFactory.cpp; path = ../../runtime/TokenFactory.cpp; sourceTree = SOURCE_ROOT; };
27C6669F1C9584050021E494 /* TokenFactory.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TokenFactory.h; path = ../../runtime/TokenFactory.h; sourceTree = SOURCE_ROOT; }; 27C6669F1C9584050021E494 /* TokenFactory.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TokenFactory.h; path = ../../runtime/TokenFactory.h; sourceTree = SOURCE_ROOT; };
@ -693,8 +641,8 @@
27C667481C95846E0021E494 /* AbstractPredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AbstractPredicateTransition.h; sourceTree = "<group>"; }; 27C667481C95846E0021E494 /* AbstractPredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AbstractPredicateTransition.h; sourceTree = "<group>"; };
27C667491C95846E0021E494 /* ActionTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ActionTransition.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C667491C95846E0021E494 /* ActionTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ActionTransition.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6674A1C95846E0021E494 /* ActionTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ActionTransition.h; sourceTree = "<group>"; }; 27C6674A1C95846E0021E494 /* ActionTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ActionTransition.h; sourceTree = "<group>"; };
27C6674B1C95846E0021E494 /* ArrayPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ArrayPredictionContext.cpp; sourceTree = "<group>"; }; 27C6674B1C95846E0021E494 /* ArrayPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ArrayPredictionContext.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6674C1C95846E0021E494 /* ArrayPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ArrayPredictionContext.h; sourceTree = "<group>"; }; 27C6674C1C95846E0021E494 /* ArrayPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ArrayPredictionContext.h; sourceTree = "<group>"; wrapsLines = 0; };
27C6674D1C95846E0021E494 /* ATN.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ATN.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6674D1C95846E0021E494 /* ATN.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ATN.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6674E1C95846E0021E494 /* ATN.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ATN.h; sourceTree = "<group>"; }; 27C6674E1C95846E0021E494 /* ATN.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ATN.h; sourceTree = "<group>"; };
27C6674F1C95846E0021E494 /* ATNConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ATNConfig.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6674F1C95846E0021E494 /* ATNConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ATNConfig.cpp; sourceTree = "<group>"; wrapsLines = 0; };
@ -725,8 +673,8 @@
27C667681C95846E0021E494 /* BlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = BlockStartState.h; sourceTree = "<group>"; }; 27C667681C95846E0021E494 /* BlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = BlockStartState.h; sourceTree = "<group>"; };
27C667691C95846E0021E494 /* DecisionState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = DecisionState.cpp; sourceTree = "<group>"; }; 27C667691C95846E0021E494 /* DecisionState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = DecisionState.cpp; sourceTree = "<group>"; };
27C6676A1C95846E0021E494 /* DecisionState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DecisionState.h; sourceTree = "<group>"; }; 27C6676A1C95846E0021E494 /* DecisionState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DecisionState.h; sourceTree = "<group>"; };
27C6676B1C95846E0021E494 /* EmptyPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EmptyPredictionContext.cpp; sourceTree = "<group>"; }; 27C6676B1C95846E0021E494 /* EmptyPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EmptyPredictionContext.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6676C1C95846E0021E494 /* EmptyPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EmptyPredictionContext.h; sourceTree = "<group>"; }; 27C6676C1C95846E0021E494 /* EmptyPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EmptyPredictionContext.h; sourceTree = "<group>"; wrapsLines = 0; };
27C6676D1C95846E0021E494 /* EpsilonTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EpsilonTransition.cpp; sourceTree = "<group>"; }; 27C6676D1C95846E0021E494 /* EpsilonTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EpsilonTransition.cpp; sourceTree = "<group>"; };
27C6676E1C95846E0021E494 /* EpsilonTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EpsilonTransition.h; sourceTree = "<group>"; }; 27C6676E1C95846E0021E494 /* EpsilonTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EpsilonTransition.h; sourceTree = "<group>"; };
27C6676F1C95846E0021E494 /* LexerATNConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LexerATNConfig.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6676F1C95846E0021E494 /* LexerATNConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LexerATNConfig.cpp; sourceTree = "<group>"; wrapsLines = 0; };
@ -747,14 +695,12 @@
27C6677F1C95846E0021E494 /* PlusBlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PlusBlockStartState.h; sourceTree = "<group>"; }; 27C6677F1C95846E0021E494 /* PlusBlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PlusBlockStartState.h; sourceTree = "<group>"; };
27C667801C95846E0021E494 /* PlusLoopbackState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PlusLoopbackState.cpp; sourceTree = "<group>"; }; 27C667801C95846E0021E494 /* PlusLoopbackState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PlusLoopbackState.cpp; sourceTree = "<group>"; };
27C667811C95846E0021E494 /* PlusLoopbackState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PlusLoopbackState.h; sourceTree = "<group>"; }; 27C667811C95846E0021E494 /* PlusLoopbackState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PlusLoopbackState.h; sourceTree = "<group>"; };
27C667821C95846E0021E494 /* PrecedencePredicateTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PrecedencePredicateTransition.cpp; sourceTree = "<group>"; }; 27C667821C95846E0021E494 /* PrecedencePredicateTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PrecedencePredicateTransition.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C667831C95846E0021E494 /* PrecedencePredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrecedencePredicateTransition.h; sourceTree = "<group>"; }; 27C667831C95846E0021E494 /* PrecedencePredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrecedencePredicateTransition.h; sourceTree = "<group>"; };
27C667841C95846E0021E494 /* PredicateTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredicateTransition.cpp; sourceTree = "<group>"; }; 27C667841C95846E0021E494 /* PredicateTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredicateTransition.cpp; sourceTree = "<group>"; };
27C667851C95846E0021E494 /* PredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredicateTransition.h; sourceTree = "<group>"; }; 27C667851C95846E0021E494 /* PredicateTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredicateTransition.h; sourceTree = "<group>"; };
27C667861C95846E0021E494 /* PredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredictionContext.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C667861C95846E0021E494 /* PredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredictionContext.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C667871C95846E0021E494 /* PredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredictionContext.h; sourceTree = "<group>"; }; 27C667871C95846E0021E494 /* PredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredictionContext.h; sourceTree = "<group>"; wrapsLines = 0; };
27C667881C95846E0021E494 /* PredictionContextCache.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredictionContextCache.cpp; sourceTree = "<group>"; };
27C667891C95846E0021E494 /* PredictionContextCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredictionContextCache.h; sourceTree = "<group>"; };
27C6678A1C95846E0021E494 /* PredictionMode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredictionMode.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6678A1C95846E0021E494 /* PredictionMode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PredictionMode.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6678B1C95846E0021E494 /* PredictionMode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredictionMode.h; sourceTree = "<group>"; }; 27C6678B1C95846E0021E494 /* PredictionMode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PredictionMode.h; sourceTree = "<group>"; };
27C6678C1C95846E0021E494 /* RangeTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RangeTransition.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6678C1C95846E0021E494 /* RangeTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RangeTransition.cpp; sourceTree = "<group>"; wrapsLines = 0; };
@ -769,8 +715,8 @@
27C667951C95846E0021E494 /* SemanticContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SemanticContext.h; sourceTree = "<group>"; }; 27C667951C95846E0021E494 /* SemanticContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SemanticContext.h; sourceTree = "<group>"; };
27C667961C95846E0021E494 /* SetTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SetTransition.cpp; sourceTree = "<group>"; }; 27C667961C95846E0021E494 /* SetTransition.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SetTransition.cpp; sourceTree = "<group>"; };
27C667971C95846E0021E494 /* SetTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SetTransition.h; sourceTree = "<group>"; }; 27C667971C95846E0021E494 /* SetTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SetTransition.h; sourceTree = "<group>"; };
27C667981C95846E0021E494 /* SingletonPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SingletonPredictionContext.cpp; sourceTree = "<group>"; }; 27C667981C95846E0021E494 /* SingletonPredictionContext.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SingletonPredictionContext.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C667991C95846E0021E494 /* SingletonPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SingletonPredictionContext.h; sourceTree = "<group>"; }; 27C667991C95846E0021E494 /* SingletonPredictionContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SingletonPredictionContext.h; sourceTree = "<group>"; wrapsLines = 0; };
27C6679A1C95846E0021E494 /* StarBlockStartState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StarBlockStartState.cpp; sourceTree = "<group>"; }; 27C6679A1C95846E0021E494 /* StarBlockStartState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StarBlockStartState.cpp; sourceTree = "<group>"; };
27C6679B1C95846E0021E494 /* StarBlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StarBlockStartState.h; sourceTree = "<group>"; }; 27C6679B1C95846E0021E494 /* StarBlockStartState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StarBlockStartState.h; sourceTree = "<group>"; };
27C6679C1C95846E0021E494 /* StarLoopbackState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StarLoopbackState.cpp; sourceTree = "<group>"; }; 27C6679C1C95846E0021E494 /* StarLoopbackState.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StarLoopbackState.cpp; sourceTree = "<group>"; };
@ -791,23 +737,14 @@
27C6686A1C9584B60021E494 /* DFAState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DFAState.h; sourceTree = "<group>"; }; 27C6686A1C9584B60021E494 /* DFAState.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DFAState.h; sourceTree = "<group>"; };
27C6686B1C9584B60021E494 /* LexerDFASerializer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LexerDFASerializer.cpp; sourceTree = "<group>"; }; 27C6686B1C9584B60021E494 /* LexerDFASerializer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LexerDFASerializer.cpp; sourceTree = "<group>"; };
27C6686C1C9584B60021E494 /* LexerDFASerializer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LexerDFASerializer.h; sourceTree = "<group>"; }; 27C6686C1C9584B60021E494 /* LexerDFASerializer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LexerDFASerializer.h; sourceTree = "<group>"; };
27C668821C9584FA0021E494 /* DoubleKeyMap.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DoubleKeyMap.h; sourceTree = "<group>"; };
27C668841C9584FA0021E494 /* EqualityComparator.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EqualityComparator.cpp; sourceTree = "<group>"; }; 27C668841C9584FA0021E494 /* EqualityComparator.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EqualityComparator.cpp; sourceTree = "<group>"; };
27C668851C9584FA0021E494 /* EqualityComparator.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EqualityComparator.h; sourceTree = "<group>"; }; 27C668851C9584FA0021E494 /* EqualityComparator.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = EqualityComparator.h; sourceTree = "<group>"; };
27C668881C9584FA0021E494 /* Interval.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Interval.cpp; sourceTree = "<group>"; }; 27C668881C9584FA0021E494 /* Interval.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Interval.cpp; sourceTree = "<group>"; };
27C668891C9584FA0021E494 /* Interval.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Interval.h; sourceTree = "<group>"; }; 27C668891C9584FA0021E494 /* Interval.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Interval.h; sourceTree = "<group>"; };
27C6688A1C9584FA0021E494 /* IntervalSet.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = IntervalSet.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C6688A1C9584FA0021E494 /* IntervalSet.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = IntervalSet.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C6688B1C9584FA0021E494 /* IntervalSet.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = IntervalSet.h; sourceTree = "<group>"; }; 27C6688B1C9584FA0021E494 /* IntervalSet.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = IntervalSet.h; sourceTree = "<group>"; };
27C668901C9584FA0021E494 /* LogManager.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LogManager.cpp; sourceTree = "<group>"; };
27C668911C9584FA0021E494 /* LogManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LogManager.h; sourceTree = "<group>"; };
27C668921C9584FA0021E494 /* MultiMap.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MultiMap.cpp; sourceTree = "<group>"; };
27C668931C9584FA0021E494 /* MultiMap.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MultiMap.h; sourceTree = "<group>"; };
27C668941C9584FA0021E494 /* MurmurHash.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MurmurHash.cpp; sourceTree = "<group>"; }; 27C668941C9584FA0021E494 /* MurmurHash.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MurmurHash.cpp; sourceTree = "<group>"; };
27C668951C9584FA0021E494 /* MurmurHash.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MurmurHash.h; sourceTree = "<group>"; }; 27C668951C9584FA0021E494 /* MurmurHash.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MurmurHash.h; sourceTree = "<group>"; };
27C6689A1C9584FA0021E494 /* OrderedHashSet.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = OrderedHashSet.cpp; sourceTree = "<group>"; };
27C6689B1C9584FA0021E494 /* OrderedHashSet.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OrderedHashSet.h; sourceTree = "<group>"; };
27C6689C1C9584FA0021E494 /* ParseCancellationException.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ParseCancellationException.cpp; sourceTree = "<group>"; };
27C6689D1C9584FA0021E494 /* ParseCancellationException.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ParseCancellationException.h; sourceTree = "<group>"; };
27C6689E1C9584FA0021E494 /* TestRig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TestRig.cpp; sourceTree = "<group>"; }; 27C6689E1C9584FA0021E494 /* TestRig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TestRig.cpp; sourceTree = "<group>"; };
27C6689F1C9584FA0021E494 /* TestRig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TestRig.h; sourceTree = "<group>"; }; 27C6689F1C9584FA0021E494 /* TestRig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TestRig.h; sourceTree = "<group>"; };
27C668EA1C9585230021E494 /* Arrays.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Arrays.cpp; sourceTree = "<group>"; }; 27C668EA1C9585230021E494 /* Arrays.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Arrays.cpp; sourceTree = "<group>"; };
@ -850,9 +787,9 @@
27C669871C9585B80021E494 /* Tree.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Tree.cpp; sourceTree = "<group>"; }; 27C669871C9585B80021E494 /* Tree.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Tree.cpp; sourceTree = "<group>"; };
27C669881C9585B80021E494 /* Tree.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Tree.h; sourceTree = "<group>"; }; 27C669881C9585B80021E494 /* Tree.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Tree.h; sourceTree = "<group>"; };
27C669891C9585B80021E494 /* Trees.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Trees.cpp; sourceTree = "<group>"; }; 27C669891C9585B80021E494 /* Trees.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Trees.cpp; sourceTree = "<group>"; };
27C6698A1C9585B80021E494 /* Trees.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Trees.h; sourceTree = "<group>"; }; 27C6698A1C9585B80021E494 /* Trees.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Trees.h; sourceTree = "<group>"; wrapsLines = 0; };
27C669F01C958AB30021E494 /* Chunk.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Chunk.cpp; path = pattern/Chunk.cpp; sourceTree = "<group>"; }; 27C669F01C958AB30021E494 /* Chunk.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Chunk.cpp; path = pattern/Chunk.cpp; sourceTree = "<group>"; };
27C669F11C958AB30021E494 /* ParseTreeMatch.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreeMatch.cpp; path = pattern/ParseTreeMatch.cpp; sourceTree = "<group>"; }; 27C669F11C958AB30021E494 /* ParseTreeMatch.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreeMatch.cpp; path = pattern/ParseTreeMatch.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C669F21C958AB30021E494 /* ParseTreePattern.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreePattern.cpp; path = pattern/ParseTreePattern.cpp; sourceTree = "<group>"; }; 27C669F21C958AB30021E494 /* ParseTreePattern.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreePattern.cpp; path = pattern/ParseTreePattern.cpp; sourceTree = "<group>"; };
27C669F31C958AB30021E494 /* ParseTreePatternMatcher.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreePatternMatcher.cpp; path = pattern/ParseTreePatternMatcher.cpp; sourceTree = "<group>"; wrapsLines = 0; }; 27C669F31C958AB30021E494 /* ParseTreePatternMatcher.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ParseTreePatternMatcher.cpp; path = pattern/ParseTreePatternMatcher.cpp; sourceTree = "<group>"; wrapsLines = 0; };
27C669F41C958AB30021E494 /* RuleTagToken.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = RuleTagToken.cpp; path = pattern/RuleTagToken.cpp; sourceTree = "<group>"; }; 27C669F41C958AB30021E494 /* RuleTagToken.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = RuleTagToken.cpp; path = pattern/RuleTagToken.cpp; sourceTree = "<group>"; };
@ -860,31 +797,13 @@
27C669F61C958AB30021E494 /* TextChunk.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TextChunk.cpp; path = pattern/TextChunk.cpp; sourceTree = "<group>"; }; 27C669F61C958AB30021E494 /* TextChunk.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TextChunk.cpp; path = pattern/TextChunk.cpp; sourceTree = "<group>"; };
27C669F71C958AB30021E494 /* TokenTagToken.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TokenTagToken.cpp; path = pattern/TokenTagToken.cpp; sourceTree = "<group>"; }; 27C669F71C958AB30021E494 /* TokenTagToken.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = TokenTagToken.cpp; path = pattern/TokenTagToken.cpp; sourceTree = "<group>"; };
27C669F81C958AB30021E494 /* Chunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Chunk.h; path = pattern/Chunk.h; sourceTree = "<group>"; }; 27C669F81C958AB30021E494 /* Chunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Chunk.h; path = pattern/Chunk.h; sourceTree = "<group>"; };
27C669F91C958AB30021E494 /* ParseTreeMatch.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreeMatch.h; path = pattern/ParseTreeMatch.h; sourceTree = "<group>"; }; 27C669F91C958AB30021E494 /* ParseTreeMatch.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreeMatch.h; path = pattern/ParseTreeMatch.h; sourceTree = "<group>"; wrapsLines = 0; };
27C669FA1C958AB30021E494 /* ParseTreePattern.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreePattern.h; path = pattern/ParseTreePattern.h; sourceTree = "<group>"; }; 27C669FA1C958AB30021E494 /* ParseTreePattern.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreePattern.h; path = pattern/ParseTreePattern.h; sourceTree = "<group>"; };
27C669FB1C958AB30021E494 /* ParseTreePatternMatcher.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreePatternMatcher.h; path = pattern/ParseTreePatternMatcher.h; sourceTree = "<group>"; }; 27C669FB1C958AB30021E494 /* ParseTreePatternMatcher.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ParseTreePatternMatcher.h; path = pattern/ParseTreePatternMatcher.h; sourceTree = "<group>"; wrapsLines = 0; };
27C669FC1C958AB30021E494 /* RuleTagToken.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RuleTagToken.h; path = pattern/RuleTagToken.h; sourceTree = "<group>"; }; 27C669FC1C958AB30021E494 /* RuleTagToken.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RuleTagToken.h; path = pattern/RuleTagToken.h; sourceTree = "<group>"; };
27C669FD1C958AB30021E494 /* TagChunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TagChunk.h; path = pattern/TagChunk.h; sourceTree = "<group>"; }; 27C669FD1C958AB30021E494 /* TagChunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TagChunk.h; path = pattern/TagChunk.h; sourceTree = "<group>"; };
27C669FE1C958AB30021E494 /* TextChunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TextChunk.h; path = pattern/TextChunk.h; sourceTree = "<group>"; }; 27C669FE1C958AB30021E494 /* TextChunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TextChunk.h; path = pattern/TextChunk.h; sourceTree = "<group>"; };
27C669FF1C958AB30021E494 /* TokenTagToken.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TokenTagToken.h; path = pattern/TokenTagToken.h; sourceTree = "<group>"; }; 27C669FF1C958AB30021E494 /* TokenTagToken.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = TokenTagToken.h; path = pattern/TokenTagToken.h; sourceTree = "<group>"; };
27C66A201C958AC10021E494 /* XPath.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPath.cpp; path = xpath/XPath.cpp; sourceTree = "<group>"; };
27C66A211C958AC10021E494 /* XPathElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathElement.cpp; path = xpath/XPathElement.cpp; sourceTree = "<group>"; };
27C66A231C958AC10021E494 /* XPathLexerErrorListener.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathLexerErrorListener.cpp; path = xpath/XPathLexerErrorListener.cpp; sourceTree = "<group>"; };
27C66A241C958AC10021E494 /* XPathRuleAnywhereElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathRuleAnywhereElement.cpp; path = xpath/XPathRuleAnywhereElement.cpp; sourceTree = "<group>"; };
27C66A251C958AC10021E494 /* XPathRuleElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathRuleElement.cpp; path = xpath/XPathRuleElement.cpp; sourceTree = "<group>"; };
27C66A261C958AC10021E494 /* XPathTokenAnywhereElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathTokenAnywhereElement.cpp; path = xpath/XPathTokenAnywhereElement.cpp; sourceTree = "<group>"; };
27C66A271C958AC10021E494 /* XPathTokenElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathTokenElement.cpp; path = xpath/XPathTokenElement.cpp; sourceTree = "<group>"; };
27C66A281C958AC10021E494 /* XPathWildcardAnywhereElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathWildcardAnywhereElement.cpp; path = xpath/XPathWildcardAnywhereElement.cpp; sourceTree = "<group>"; };
27C66A291C958AC10021E494 /* XPathWildcardElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = XPathWildcardElement.cpp; path = xpath/XPathWildcardElement.cpp; sourceTree = "<group>"; };
27C66A2A1C958AC10021E494 /* XPath.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPath.h; path = xpath/XPath.h; sourceTree = "<group>"; };
27C66A2B1C958AC10021E494 /* XPathElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathElement.h; path = xpath/XPathElement.h; sourceTree = "<group>"; };
27C66A2D1C958AC10021E494 /* XPathLexerErrorListener.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathLexerErrorListener.h; path = xpath/XPathLexerErrorListener.h; sourceTree = "<group>"; };
27C66A2E1C958AC10021E494 /* XPathRuleAnywhereElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathRuleAnywhereElement.h; path = xpath/XPathRuleAnywhereElement.h; sourceTree = "<group>"; };
27C66A2F1C958AC10021E494 /* XPathRuleElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathRuleElement.h; path = xpath/XPathRuleElement.h; sourceTree = "<group>"; };
27C66A301C958AC10021E494 /* XPathTokenAnywhereElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathTokenAnywhereElement.h; path = xpath/XPathTokenAnywhereElement.h; sourceTree = "<group>"; };
27C66A311C958AC10021E494 /* XPathTokenElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathTokenElement.h; path = xpath/XPathTokenElement.h; sourceTree = "<group>"; };
27C66A321C958AC10021E494 /* XPathWildcardAnywhereElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathWildcardAnywhereElement.h; path = xpath/XPathWildcardAnywhereElement.h; sourceTree = "<group>"; };
27C66A331C958AC10021E494 /* XPathWildcardElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = XPathWildcardElement.h; path = xpath/XPathWildcardElement.h; sourceTree = "<group>"; };
27C66A671C9591280021E494 /* antlr4-cpp-demo */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = "antlr4-cpp-demo"; sourceTree = BUILT_PRODUCTS_DIR; }; 27C66A671C9591280021E494 /* antlr4-cpp-demo */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = "antlr4-cpp-demo"; sourceTree = BUILT_PRODUCTS_DIR; };
27C66A691C9591280021E494 /* main.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = main.cpp; sourceTree = "<group>"; }; 27C66A691C9591280021E494 /* main.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = main.cpp; sourceTree = "<group>"; };
27C66A731C9592400021E494 /* TLexer.g4 */ = {isa = PBXFileReference; lastKnownFileType = text; name = TLexer.g4; path = ../../TLexer.g4; sourceTree = "<group>"; }; 27C66A731C9592400021E494 /* TLexer.g4 */ = {isa = PBXFileReference; lastKnownFileType = text; name = TLexer.g4; path = ../../TLexer.g4; sourceTree = "<group>"; };
@ -942,6 +861,36 @@
/* End PBXFrameworksBuildPhase section */ /* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */ /* Begin PBXGroup section */
27BC755F1CB41B1100AE780B /* Simple */ = {
isa = PBXGroup;
children = (
27BC75591CB41B0D00AE780B /* TestLexer.cpp */,
27BC755A1CB41B0D00AE780B /* TestLexer.h */,
27BC755B1CB41B0D00AE780B /* TestParser.cpp */,
27BC755C1CB41B0D00AE780B /* TestParser.h */,
27C6E1711C972FFB0079AF06 /* TLexer.cpp */,
27C6E1721C972FFC0079AF06 /* TLexer.h */,
);
name = Simple;
sourceTree = "<group>";
};
27BC75601CB41B2400AE780B /* Advanced */ = {
isa = PBXGroup;
children = (
27C6E1741C972FFC0079AF06 /* TParser.cpp */,
27C6E1751C972FFC0079AF06 /* TParser.h */,
27C6E1771C972FFC0079AF06 /* TParserBaseListener.cpp */,
27C6E1781C972FFC0079AF06 /* TParserBaseListener.h */,
27C6E1791C972FFC0079AF06 /* TParserBaseVisitor.cpp */,
27C6E1851C97322F0079AF06 /* TParserBaseVisitor.h */,
27C6E17B1C972FFC0079AF06 /* TParserListener.cpp */,
27C6E17C1C972FFC0079AF06 /* TParserListener.h */,
27C6E17D1C972FFC0079AF06 /* TParserVisitor.cpp */,
27C6E1861C97322F0079AF06 /* TParserVisitor.h */,
);
name = Advanced;
sourceTree = "<group>";
};
27C667461C9584570021E494 /* atn */ = { 27C667461C9584570021E494 /* atn */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
@ -1009,8 +958,6 @@
27C667851C95846E0021E494 /* PredicateTransition.h */, 27C667851C95846E0021E494 /* PredicateTransition.h */,
27C667861C95846E0021E494 /* PredictionContext.cpp */, 27C667861C95846E0021E494 /* PredictionContext.cpp */,
27C667871C95846E0021E494 /* PredictionContext.h */, 27C667871C95846E0021E494 /* PredictionContext.h */,
27C667881C95846E0021E494 /* PredictionContextCache.cpp */,
27C667891C95846E0021E494 /* PredictionContextCache.h */,
27C6678A1C95846E0021E494 /* PredictionMode.cpp */, 27C6678A1C95846E0021E494 /* PredictionMode.cpp */,
27C6678B1C95846E0021E494 /* PredictionMode.h */, 27C6678B1C95846E0021E494 /* PredictionMode.h */,
27C6678C1C95846E0021E494 /* RangeTransition.cpp */, 27C6678C1C95846E0021E494 /* RangeTransition.cpp */,
@ -1063,23 +1010,14 @@
27C6687D1C9584E90021E494 /* misc */ = { 27C6687D1C9584E90021E494 /* misc */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
27C668821C9584FA0021E494 /* DoubleKeyMap.h */,
27C668841C9584FA0021E494 /* EqualityComparator.cpp */, 27C668841C9584FA0021E494 /* EqualityComparator.cpp */,
27C668851C9584FA0021E494 /* EqualityComparator.h */, 27C668851C9584FA0021E494 /* EqualityComparator.h */,
27C668881C9584FA0021E494 /* Interval.cpp */, 27C668881C9584FA0021E494 /* Interval.cpp */,
27C668891C9584FA0021E494 /* Interval.h */, 27C668891C9584FA0021E494 /* Interval.h */,
27C6688A1C9584FA0021E494 /* IntervalSet.cpp */, 27C6688A1C9584FA0021E494 /* IntervalSet.cpp */,
27C6688B1C9584FA0021E494 /* IntervalSet.h */, 27C6688B1C9584FA0021E494 /* IntervalSet.h */,
27C668901C9584FA0021E494 /* LogManager.cpp */,
27C668911C9584FA0021E494 /* LogManager.h */,
27C668921C9584FA0021E494 /* MultiMap.cpp */,
27C668931C9584FA0021E494 /* MultiMap.h */,
27C668941C9584FA0021E494 /* MurmurHash.cpp */, 27C668941C9584FA0021E494 /* MurmurHash.cpp */,
27C668951C9584FA0021E494 /* MurmurHash.h */, 27C668951C9584FA0021E494 /* MurmurHash.h */,
27C6689A1C9584FA0021E494 /* OrderedHashSet.cpp */,
27C6689B1C9584FA0021E494 /* OrderedHashSet.h */,
27C6689C1C9584FA0021E494 /* ParseCancellationException.cpp */,
27C6689D1C9584FA0021E494 /* ParseCancellationException.h */,
27C6689E1C9584FA0021E494 /* TestRig.cpp */, 27C6689E1C9584FA0021E494 /* TestRig.cpp */,
27C6689F1C9584FA0021E494 /* TestRig.h */, 27C6689F1C9584FA0021E494 /* TestRig.h */,
); );
@ -1110,7 +1048,6 @@
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
27C669C41C958A8C0021E494 /* pattern */, 27C669C41C958A8C0021E494 /* pattern */,
27C669C51C958A920021E494 /* xpath */,
27C6696F1C9585B80021E494 /* AbstractParseTreeVisitor.cpp */, 27C6696F1C9585B80021E494 /* AbstractParseTreeVisitor.cpp */,
27C669701C9585B80021E494 /* AbstractParseTreeVisitor.h */, 27C669701C9585B80021E494 /* AbstractParseTreeVisitor.h */,
27C669711C9585B80021E494 /* ErrorNode.cpp */, 27C669711C9585B80021E494 /* ErrorNode.cpp */,
@ -1166,46 +1103,11 @@
name = pattern; name = pattern;
sourceTree = "<group>"; sourceTree = "<group>";
}; };
27C669C51C958A920021E494 /* xpath */ = {
isa = PBXGroup;
children = (
27C66A201C958AC10021E494 /* XPath.cpp */,
27C66A2A1C958AC10021E494 /* XPath.h */,
27C66A211C958AC10021E494 /* XPathElement.cpp */,
27C66A2B1C958AC10021E494 /* XPathElement.h */,
27C66A231C958AC10021E494 /* XPathLexerErrorListener.cpp */,
27C66A2D1C958AC10021E494 /* XPathLexerErrorListener.h */,
27C66A241C958AC10021E494 /* XPathRuleAnywhereElement.cpp */,
27C66A2E1C958AC10021E494 /* XPathRuleAnywhereElement.h */,
27C66A251C958AC10021E494 /* XPathRuleElement.cpp */,
27C66A2F1C958AC10021E494 /* XPathRuleElement.h */,
27C66A261C958AC10021E494 /* XPathTokenAnywhereElement.cpp */,
27C66A301C958AC10021E494 /* XPathTokenAnywhereElement.h */,
27C66A271C958AC10021E494 /* XPathTokenElement.cpp */,
27C66A311C958AC10021E494 /* XPathTokenElement.h */,
27C66A281C958AC10021E494 /* XPathWildcardAnywhereElement.cpp */,
27C66A321C958AC10021E494 /* XPathWildcardAnywhereElement.h */,
27C66A291C958AC10021E494 /* XPathWildcardElement.cpp */,
27C66A331C958AC10021E494 /* XPathWildcardElement.h */,
);
name = xpath;
sourceTree = "<group>";
};
27C66A5C1C958EB50021E494 /* generated */ = { 27C66A5C1C958EB50021E494 /* generated */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
27C6E1711C972FFB0079AF06 /* TLexer.cpp */, 27BC75601CB41B2400AE780B /* Advanced */,
27C6E1721C972FFC0079AF06 /* TLexer.h */, 27BC755F1CB41B1100AE780B /* Simple */,
27C6E1741C972FFC0079AF06 /* TParser.cpp */,
27C6E1751C972FFC0079AF06 /* TParser.h */,
27C6E1771C972FFC0079AF06 /* TParserBaseListener.cpp */,
27C6E1781C972FFC0079AF06 /* TParserBaseListener.h */,
27C6E1791C972FFC0079AF06 /* TParserBaseVisitor.cpp */,
27C6E1851C97322F0079AF06 /* TParserBaseVisitor.h */,
27C6E17B1C972FFC0079AF06 /* TParserListener.cpp */,
27C6E17C1C972FFC0079AF06 /* TParserListener.h */,
27C6E17D1C972FFC0079AF06 /* TParserVisitor.cpp */,
27C6E1861C97322F0079AF06 /* TParserVisitor.h */,
); );
name = generated; name = generated;
sourceTree = "<group>"; sourceTree = "<group>";
@ -1363,13 +1265,11 @@
files = ( files = (
27C668431C95846E0021E494 /* SemanticContext.h in Headers */, 27C668431C95846E0021E494 /* SemanticContext.h in Headers */,
27C667B51C95846E0021E494 /* ATN.h in Headers */, 27C667B51C95846E0021E494 /* ATN.h in Headers */,
27C66A591C958AC10021E494 /* XPathWildcardAnywhereElement.h in Headers */,
27C668471C95846E0021E494 /* SetTransition.h in Headers */, 27C668471C95846E0021E494 /* SetTransition.h in Headers */,
27C667DD1C95846E0021E494 /* BasicBlockStartState.h in Headers */, 27C667DD1C95846E0021E494 /* BasicBlockStartState.h in Headers */,
27C667111C9584050021E494 /* Parser.h in Headers */, 27C667111C9584050021E494 /* Parser.h in Headers */,
27C6684B1C95846E0021E494 /* SingletonPredictionContext.h in Headers */, 27C6684B1C95846E0021E494 /* SingletonPredictionContext.h in Headers */,
27C669C21C9585B80021E494 /* Trees.h in Headers */, 27C669C21C9585B80021E494 /* Trees.h in Headers */,
27C66A511C958AC10021E494 /* XPathRuleAnywhereElement.h in Headers */,
27C6672F1C9584050021E494 /* TokenFactory.h in Headers */, 27C6672F1C9584050021E494 /* TokenFactory.h in Headers */,
27C669071C9585230021E494 /* CPPUtils.h in Headers */, 27C669071C9585230021E494 /* CPPUtils.h in Headers */,
27C666C11C9584050021E494 /* BaseErrorListener.h in Headers */, 27C666C11C9584050021E494 /* BaseErrorListener.h in Headers */,
@ -1402,17 +1302,14 @@
27C667371C9584050021E494 /* TokenStream.h in Headers */, 27C667371C9584050021E494 /* TokenStream.h in Headers */,
27C6682F1C95846E0021E494 /* PredictionMode.h in Headers */, 27C6682F1C95846E0021E494 /* PredictionMode.h in Headers */,
27C669A61C9585B80021E494 /* ParseTreeVisitor.h in Headers */, 27C669A61C9585B80021E494 /* ParseTreeVisitor.h in Headers */,
27C66A4B1C958AC10021E494 /* XPathElement.h in Headers */,
27C668741C9584B60021E494 /* DFASerializer.h in Headers */, 27C668741C9584B60021E494 /* DFASerializer.h in Headers */,
27C669961C9585B80021E494 /* ErrorNodeImpl.h in Headers */, 27C669961C9585B80021E494 /* ErrorNodeImpl.h in Headers */,
27C667C91C95846E0021E494 /* ATNSerializer.h in Headers */, 27C667C91C95846E0021E494 /* ATNSerializer.h in Headers */,
27C66A191C958AB30021E494 /* RuleTagToken.h in Headers */, 27C66A191C958AB30021E494 /* RuleTagToken.h in Headers */,
27C667411C9584050021E494 /* UnbufferedTokenStream.h in Headers */, 27C667411C9584050021E494 /* UnbufferedTokenStream.h in Headers */,
27C668131C95846E0021E494 /* ParserATNSimulator.h in Headers */, 27C668131C95846E0021E494 /* ParserATNSimulator.h in Headers */,
27C668C51C9584FA0021E494 /* LogManager.h in Headers */,
27C667051C9584050021E494 /* LexerNoViableAltException.h in Headers */, 27C667051C9584050021E494 /* LexerNoViableAltException.h in Headers */,
27C666B51C9584050021E494 /* ANTLRFileStream.h in Headers */, 27C666B51C9584050021E494 /* ANTLRFileStream.h in Headers */,
27C66A491C958AC10021E494 /* XPath.h in Headers */,
27C667B11C95846E0021E494 /* ArrayPredictionContext.h in Headers */, 27C667B11C95846E0021E494 /* ArrayPredictionContext.h in Headers */,
2747A70D1CA691310030247B /* ConfigLookup.h in Headers */, 2747A70D1CA691310030247B /* ConfigLookup.h in Headers */,
27C669AE1C9585B80021E494 /* RuleNode.h in Headers */, 27C669AE1C9585B80021E494 /* RuleNode.h in Headers */,
@ -1444,28 +1341,22 @@
27C666B11C9584050021E494 /* ANTLRErrorStrategy.h in Headers */, 27C666B11C9584050021E494 /* ANTLRErrorStrategy.h in Headers */,
27C667B91C95846E0021E494 /* ATNConfig.h in Headers */, 27C667B91C95846E0021E494 /* ATNConfig.h in Headers */,
27C6690F1C9585230021E494 /* stringconverter.h in Headers */, 27C6690F1C9585230021E494 /* stringconverter.h in Headers */,
27C668DD1C9584FA0021E494 /* ParseCancellationException.h in Headers */,
27C6670D1C9584050021E494 /* NoViableAltException.h in Headers */, 27C6670D1C9584050021E494 /* NoViableAltException.h in Headers */,
27C6699E1C9585B80021E494 /* ParseTreeListener.h in Headers */, 27C6699E1C9585B80021E494 /* ParseTreeListener.h in Headers */,
27C6681B1C95846E0021E494 /* PlusLoopbackState.h in Headers */, 27C6681B1C95846E0021E494 /* PlusLoopbackState.h in Headers */,
27C666F71C9584050021E494 /* IntStream.h in Headers */, 27C666F71C9584050021E494 /* IntStream.h in Headers */,
27C6683B1C95846E0021E494 /* RuleStopState.h in Headers */, 27C6683B1C95846E0021E494 /* RuleStopState.h in Headers */,
27C6682B1C95846E0021E494 /* PredictionContextCache.h in Headers */,
27C66A5B1C958AC10021E494 /* XPathWildcardElement.h in Headers */,
27C668781C9584B60021E494 /* DFAState.h in Headers */, 27C668781C9584B60021E494 /* DFAState.h in Headers */,
27C66A131C958AB30021E494 /* ParseTreeMatch.h in Headers */, 27C66A131C958AB30021E494 /* ParseTreeMatch.h in Headers */,
27C668D91C9584FA0021E494 /* OrderedHashSet.h in Headers */,
27C66A151C958AB30021E494 /* ParseTreePattern.h in Headers */, 27C66A151C958AB30021E494 /* ParseTreePattern.h in Headers */,
27C667ED1C95846E0021E494 /* DecisionState.h in Headers */, 27C667ED1C95846E0021E494 /* DecisionState.h in Headers */,
27C667FD1C95846E0021E494 /* LexerATNSimulator.h in Headers */, 27C667FD1C95846E0021E494 /* LexerATNSimulator.h in Headers */,
27C668571C95846E0021E494 /* StarLoopEntryState.h in Headers */, 27C668571C95846E0021E494 /* StarLoopEntryState.h in Headers */,
27C66A571C958AC10021E494 /* XPathTokenElement.h in Headers */,
27C6683F1C95846E0021E494 /* RuleTransition.h in Headers */, 27C6683F1C95846E0021E494 /* RuleTransition.h in Headers */,
27C667231C9584050021E494 /* Recognizer.h in Headers */, 27C667231C9584050021E494 /* Recognizer.h in Headers */,
27C6690D1C9585230021E494 /* StringBuilder.h in Headers */, 27C6690D1C9585230021E494 /* StringBuilder.h in Headers */,
27C667F11C95846E0021E494 /* EmptyPredictionContext.h in Headers */, 27C667F11C95846E0021E494 /* EmptyPredictionContext.h in Headers */,
27C667331C9584050021E494 /* TokenSource.h in Headers */, 27C667331C9584050021E494 /* TokenSource.h in Headers */,
27C66A531C958AC10021E494 /* XPathRuleElement.h in Headers */,
27C6684F1C95846E0021E494 /* StarBlockStartState.h in Headers */, 27C6684F1C95846E0021E494 /* StarBlockStartState.h in Headers */,
27C668231C95846E0021E494 /* PredicateTransition.h in Headers */, 27C668231C95846E0021E494 /* PredicateTransition.h in Headers */,
27C668011C95846E0021E494 /* LL1Analyzer.h in Headers */, 27C668011C95846E0021E494 /* LL1Analyzer.h in Headers */,
@ -1473,11 +1364,9 @@
27C668CD1C9584FA0021E494 /* MurmurHash.h in Headers */, 27C668CD1C9584FA0021E494 /* MurmurHash.h in Headers */,
27C66A171C958AB30021E494 /* ParseTreePatternMatcher.h in Headers */, 27C66A171C958AB30021E494 /* ParseTreePatternMatcher.h in Headers */,
27C667271C9584050021E494 /* RuleContext.h in Headers */, 27C667271C9584050021E494 /* RuleContext.h in Headers */,
27C668C91C9584FA0021E494 /* MultiMap.h in Headers */,
27C668631C95846E0021E494 /* WildcardTransition.h in Headers */, 27C668631C95846E0021E494 /* WildcardTransition.h in Headers */,
27C667C11C95846E0021E494 /* ATNDeserializationOptions.h in Headers */, 27C667C11C95846E0021E494 /* ATNDeserializationOptions.h in Headers */,
27C667BD1C95846E0021E494 /* ATNConfigSet.h in Headers */, 27C667BD1C95846E0021E494 /* ATNConfigSet.h in Headers */,
27C668A91C9584FA0021E494 /* DoubleKeyMap.h in Headers */,
27C667F51C95846E0021E494 /* EpsilonTransition.h in Headers */, 27C667F51C95846E0021E494 /* EpsilonTransition.h in Headers */,
27C667F91C95846E0021E494 /* LexerATNConfig.h in Headers */, 27C667F91C95846E0021E494 /* LexerATNConfig.h in Headers */,
27C668AD1C9584FA0021E494 /* EqualityComparator.h in Headers */, 27C668AD1C9584FA0021E494 /* EqualityComparator.h in Headers */,
@ -1486,14 +1375,12 @@
27C668171C95846E0021E494 /* PlusBlockStartState.h in Headers */, 27C668171C95846E0021E494 /* PlusBlockStartState.h in Headers */,
27C668271C95846E0021E494 /* PredictionContext.h in Headers */, 27C668271C95846E0021E494 /* PredictionContext.h in Headers */,
27C667011C9584050021E494 /* LexerInterpreter.h in Headers */, 27C667011C9584050021E494 /* LexerInterpreter.h in Headers */,
27C66A551C958AC10021E494 /* XPathTokenAnywhereElement.h in Headers */,
27C668701C9584B60021E494 /* DFA.h in Headers */, 27C668701C9584B60021E494 /* DFA.h in Headers */,
27C666D11C9584050021E494 /* CommonTokenFactory.h in Headers */, 27C666D11C9584050021E494 /* CommonTokenFactory.h in Headers */,
27C6680B1C95846E0021E494 /* NotSetTransition.h in Headers */, 27C6680B1C95846E0021E494 /* NotSetTransition.h in Headers */,
27C667E91C95846E0021E494 /* BlockStartState.h in Headers */, 27C667E91C95846E0021E494 /* BlockStartState.h in Headers */,
27C666F91C9584050021E494 /* IRecognizer.h in Headers */, 27C666F91C9584050021E494 /* IRecognizer.h in Headers */,
276927251C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */, 276927251C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */,
27C66A4F1C958AC10021E494 /* XPathLexerErrorListener.h in Headers */,
27C669A21C9585B80021E494 /* ParseTreeProperty.h in Headers */, 27C669A21C9585B80021E494 /* ParseTreeProperty.h in Headers */,
27C667A91C95846E0021E494 /* AbstractPredicateTransition.h in Headers */, 27C667A91C95846E0021E494 /* AbstractPredicateTransition.h in Headers */,
27C669171C9585230021E494 /* guid.h in Headers */, 27C669171C9585230021E494 /* guid.h in Headers */,
@ -1512,17 +1399,13 @@
files = ( files = (
27C666E01C9584050021E494 /* DiagnosticErrorListener.h in Headers */, 27C666E01C9584050021E494 /* DiagnosticErrorListener.h in Headers */,
27C667E81C95846E0021E494 /* BlockStartState.h in Headers */, 27C667E81C95846E0021E494 /* BlockStartState.h in Headers */,
27C66A581C958AC10021E494 /* XPathWildcardAnywhereElement.h in Headers */,
27C669001C9585230021E494 /* Arrays.h in Headers */, 27C669001C9585230021E494 /* Arrays.h in Headers */,
27C669A51C9585B80021E494 /* ParseTreeVisitor.h in Headers */, 27C669A51C9585B80021E494 /* ParseTreeVisitor.h in Headers */,
27C666AC1C9584050021E494 /* ANTLRErrorListener.h in Headers */, 27C666AC1C9584050021E494 /* ANTLRErrorListener.h in Headers */,
27C668C41C9584FA0021E494 /* LogManager.h in Headers */,
27C66A501C958AC10021E494 /* XPathRuleAnywhereElement.h in Headers */,
27C667DC1C95846E0021E494 /* BasicBlockStartState.h in Headers */, 27C667DC1C95846E0021E494 /* BasicBlockStartState.h in Headers */,
27C666F81C9584050021E494 /* IRecognizer.h in Headers */, 27C666F81C9584050021E494 /* IRecognizer.h in Headers */,
27C667E01C95846E0021E494 /* BasicState.h in Headers */, 27C667E01C95846E0021E494 /* BasicState.h in Headers */,
27C666C01C9584050021E494 /* BaseErrorListener.h in Headers */, 27C666C01C9584050021E494 /* BaseErrorListener.h in Headers */,
27C668A81C9584FA0021E494 /* DoubleKeyMap.h in Headers */,
27C668421C95846E0021E494 /* SemanticContext.h in Headers */, 27C668421C95846E0021E494 /* SemanticContext.h in Headers */,
27C6682E1C95846E0021E494 /* PredictionMode.h in Headers */, 27C6682E1C95846E0021E494 /* PredictionMode.h in Headers */,
27C667261C9584050021E494 /* RuleContext.h in Headers */, 27C667261C9584050021E494 /* RuleContext.h in Headers */,
@ -1547,7 +1430,6 @@
27C668521C95846E0021E494 /* StarLoopbackState.h in Headers */, 27C668521C95846E0021E494 /* StarLoopbackState.h in Headers */,
27C666D81C9584050021E494 /* ConsoleErrorListener.h in Headers */, 27C666D81C9584050021E494 /* ConsoleErrorListener.h in Headers */,
27C6684E1C95846E0021E494 /* StarBlockStartState.h in Headers */, 27C6684E1C95846E0021E494 /* StarBlockStartState.h in Headers */,
27C66A4A1C958AC10021E494 /* XPathElement.h in Headers */,
27C668221C95846E0021E494 /* PredicateTransition.h in Headers */, 27C668221C95846E0021E494 /* PredicateTransition.h in Headers */,
27C6698D1C9585B80021E494 /* AbstractParseTreeVisitor.h in Headers */, 27C6698D1C9585B80021E494 /* AbstractParseTreeVisitor.h in Headers */,
27C668621C95846E0021E494 /* WildcardTransition.h in Headers */, 27C668621C95846E0021E494 /* WildcardTransition.h in Headers */,
@ -1558,7 +1440,6 @@
27C666D01C9584050021E494 /* CommonTokenFactory.h in Headers */, 27C666D01C9584050021E494 /* CommonTokenFactory.h in Headers */,
27C6683E1C95846E0021E494 /* RuleTransition.h in Headers */, 27C6683E1C95846E0021E494 /* RuleTransition.h in Headers */,
27C667BC1C95846E0021E494 /* ATNConfigSet.h in Headers */, 27C667BC1C95846E0021E494 /* ATNConfigSet.h in Headers */,
27C66A481C958AC10021E494 /* XPath.h in Headers */,
27C666F21C9584050021E494 /* InterpreterRuleContext.h in Headers */, 27C666F21C9584050021E494 /* InterpreterRuleContext.h in Headers */,
27C667F41C95846E0021E494 /* EpsilonTransition.h in Headers */, 27C667F41C95846E0021E494 /* EpsilonTransition.h in Headers */,
27C666EE1C9584050021E494 /* InputMismatchException.h in Headers */, 27C666EE1C9584050021E494 /* InputMismatchException.h in Headers */,
@ -1572,7 +1453,6 @@
27C66A1A1C958AB30021E494 /* TagChunk.h in Headers */, 27C66A1A1C958AB30021E494 /* TagChunk.h in Headers */,
27C669C11C9585B80021E494 /* Trees.h in Headers */, 27C669C11C9585B80021E494 /* Trees.h in Headers */,
27C668E01C9584FA0021E494 /* TestRig.h in Headers */, 27C668E01C9584FA0021E494 /* TestRig.h in Headers */,
27C668C81C9584FA0021E494 /* MultiMap.h in Headers */,
27C667D81C95846E0021E494 /* AtomTransition.h in Headers */, 27C667D81C95846E0021E494 /* AtomTransition.h in Headers */,
27C6687B1C9584B60021E494 /* LexerDFASerializer.h in Headers */, 27C6687B1C9584B60021E494 /* LexerDFASerializer.h in Headers */,
27C668001C95846E0021E494 /* LL1Analyzer.h in Headers */, 27C668001C95846E0021E494 /* LL1Analyzer.h in Headers */,
@ -1581,7 +1461,6 @@
27C6684A1C95846E0021E494 /* SingletonPredictionContext.h in Headers */, 27C6684A1C95846E0021E494 /* SingletonPredictionContext.h in Headers */,
27C667041C9584050021E494 /* LexerNoViableAltException.h in Headers */, 27C667041C9584050021E494 /* LexerNoViableAltException.h in Headers */,
27C669121C9585230021E494 /* Strings.h in Headers */, 27C669121C9585230021E494 /* Strings.h in Headers */,
27C6682A1C95846E0021E494 /* PredictionContextCache.h in Headers */,
27C667E41C95846E0021E494 /* BlockEndState.h in Headers */, 27C667E41C95846E0021E494 /* BlockEndState.h in Headers */,
27C666B41C9584050021E494 /* ANTLRFileStream.h in Headers */, 27C666B41C9584050021E494 /* ANTLRFileStream.h in Headers */,
27C6685E1C95846E0021E494 /* Transition.h in Headers */, 27C6685E1C95846E0021E494 /* Transition.h in Headers */,
@ -1602,7 +1481,6 @@
27C6681A1C95846E0021E494 /* PlusLoopbackState.h in Headers */, 27C6681A1C95846E0021E494 /* PlusLoopbackState.h in Headers */,
27C669991C9585B80021E494 /* ParseTree.h in Headers */, 27C669991C9585B80021E494 /* ParseTree.h in Headers */,
27C669061C9585230021E494 /* CPPUtils.h in Headers */, 27C669061C9585230021E494 /* CPPUtils.h in Headers */,
27C66A5A1C958AC10021E494 /* XPathWildcardElement.h in Headers */,
27C6673E1C9584050021E494 /* UnbufferedCharStream.h in Headers */, 27C6673E1C9584050021E494 /* UnbufferedCharStream.h in Headers */,
27C66A121C958AB30021E494 /* ParseTreeMatch.h in Headers */, 27C66A121C958AB30021E494 /* ParseTreeMatch.h in Headers */,
27C667F81C95846E0021E494 /* LexerATNConfig.h in Headers */, 27C667F81C95846E0021E494 /* LexerATNConfig.h in Headers */,
@ -1610,12 +1488,10 @@
27C667081C9584050021E494 /* ListTokenSource.h in Headers */, 27C667081C9584050021E494 /* ListTokenSource.h in Headers */,
27C668CC1C9584FA0021E494 /* MurmurHash.h in Headers */, 27C668CC1C9584FA0021E494 /* MurmurHash.h in Headers */,
27C666C81C9584050021E494 /* CharStream.h in Headers */, 27C666C81C9584050021E494 /* CharStream.h in Headers */,
27C66A561C958AC10021E494 /* XPathTokenElement.h in Headers */,
27C668041C95846E0021E494 /* LoopEndState.h in Headers */, 27C668041C95846E0021E494 /* LoopEndState.h in Headers */,
27C6685A1C95846E0021E494 /* TokensStartState.h in Headers */, 27C6685A1C95846E0021E494 /* TokensStartState.h in Headers */,
27C668561C95846E0021E494 /* StarLoopEntryState.h in Headers */, 27C668561C95846E0021E494 /* StarLoopEntryState.h in Headers */,
27C6690C1C9585230021E494 /* StringBuilder.h in Headers */, 27C6690C1C9585230021E494 /* StringBuilder.h in Headers */,
27C66A521C958AC10021E494 /* XPathRuleElement.h in Headers */,
27C667B41C95846E0021E494 /* ATN.h in Headers */, 27C667B41C95846E0021E494 /* ATN.h in Headers */,
27C668AC1C9584FA0021E494 /* EqualityComparator.h in Headers */, 27C668AC1C9584FA0021E494 /* EqualityComparator.h in Headers */,
27C669AD1C9585B80021E494 /* RuleNode.h in Headers */, 27C669AD1C9585B80021E494 /* RuleNode.h in Headers */,
@ -1630,20 +1506,16 @@
27C669BD1C9585B80021E494 /* Tree.h in Headers */, 27C669BD1C9585B80021E494 /* Tree.h in Headers */,
27C668161C95846E0021E494 /* PlusBlockStartState.h in Headers */, 27C668161C95846E0021E494 /* PlusBlockStartState.h in Headers */,
27C667D01C95846E0021E494 /* ATNState.h in Headers */, 27C667D01C95846E0021E494 /* ATNState.h in Headers */,
27C668DC1C9584FA0021E494 /* ParseCancellationException.h in Headers */,
27C667FC1C95846E0021E494 /* LexerATNSimulator.h in Headers */, 27C667FC1C95846E0021E494 /* LexerATNSimulator.h in Headers */,
27C669A11C9585B80021E494 /* ParseTreeProperty.h in Headers */, 27C669A11C9585B80021E494 /* ParseTreeProperty.h in Headers */,
27C667F01C95846E0021E494 /* EmptyPredictionContext.h in Headers */, 27C667F01C95846E0021E494 /* EmptyPredictionContext.h in Headers */,
27C667CC1C95846E0021E494 /* ATNSimulator.h in Headers */, 27C667CC1C95846E0021E494 /* ATNSimulator.h in Headers */,
27C668D81C9584FA0021E494 /* OrderedHashSet.h in Headers */,
27C669B91C9585B80021E494 /* TerminalNodeImpl.h in Headers */, 27C669B91C9585B80021E494 /* TerminalNodeImpl.h in Headers */,
27C66A541C958AC10021E494 /* XPathTokenAnywhereElement.h in Headers */,
27C6681E1C95846E0021E494 /* PrecedencePredicateTransition.h in Headers */, 27C6681E1C95846E0021E494 /* PrecedencePredicateTransition.h in Headers */,
27C6671C1C9584050021E494 /* ProxyErrorListener.h in Headers */, 27C6671C1C9584050021E494 /* ProxyErrorListener.h in Headers */,
27C6680E1C95846E0021E494 /* OrderedATNConfigSet.h in Headers */, 27C6680E1C95846E0021E494 /* OrderedATNConfigSet.h in Headers */,
276927241C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */, 276927241C9ED49100E4EBF8 /* antlrcpp-Prefix.h in Headers */,
27C667D41C95846E0021E494 /* ATNType.h in Headers */, 27C667D41C95846E0021E494 /* ATNType.h in Headers */,
27C66A4E1C958AC10021E494 /* XPathLexerErrorListener.h in Headers */,
27C668B41C9584FA0021E494 /* Interval.h in Headers */, 27C668B41C9584FA0021E494 /* Interval.h in Headers */,
27C668461C95846E0021E494 /* SetTransition.h in Headers */, 27C668461C95846E0021E494 /* SetTransition.h in Headers */,
27C66A101C958AB30021E494 /* Chunk.h in Headers */, 27C66A101C958AB30021E494 /* Chunk.h in Headers */,
@ -1808,7 +1680,9 @@
27C6E1811C972FFC0079AF06 /* TParserBaseListener.cpp in Sources */, 27C6E1811C972FFC0079AF06 /* TParserBaseListener.cpp in Sources */,
27C6E1841C972FFC0079AF06 /* TParserVisitor.cpp in Sources */, 27C6E1841C972FFC0079AF06 /* TParserVisitor.cpp in Sources */,
27C6E1801C972FFC0079AF06 /* TParser.cpp in Sources */, 27C6E1801C972FFC0079AF06 /* TParser.cpp in Sources */,
27BC755D1CB41B0D00AE780B /* TestLexer.cpp in Sources */,
27C6E17F1C972FFC0079AF06 /* TLexer.cpp in Sources */, 27C6E17F1C972FFC0079AF06 /* TLexer.cpp in Sources */,
27BC755E1CB41B0D00AE780B /* TestParser.cpp in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
@ -1816,7 +1690,6 @@
isa = PBXSourcesBuildPhase; isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647; buildActionMask = 2147483647;
files = ( files = (
27C668DB1C9584FA0021E494 /* ParseCancellationException.cpp in Sources */,
27C668B71C9584FA0021E494 /* IntervalSet.cpp in Sources */, 27C668B71C9584FA0021E494 /* IntervalSet.cpp in Sources */,
27C668251C95846E0021E494 /* PredictionContext.cpp in Sources */, 27C668251C95846E0021E494 /* PredictionContext.cpp in Sources */,
27C668491C95846E0021E494 /* SingletonPredictionContext.cpp in Sources */, 27C668491C95846E0021E494 /* SingletonPredictionContext.cpp in Sources */,
@ -1824,10 +1697,8 @@
27C667CF1C95846E0021E494 /* ATNState.cpp in Sources */, 27C667CF1C95846E0021E494 /* ATNState.cpp in Sources */,
27C667AF1C95846E0021E494 /* ArrayPredictionContext.cpp in Sources */, 27C667AF1C95846E0021E494 /* ArrayPredictionContext.cpp in Sources */,
27C669981C9585B80021E494 /* ParseTree.cpp in Sources */, 27C669981C9585B80021E494 /* ParseTree.cpp in Sources */,
27C66A411C958AC10021E494 /* XPathTokenAnywhereElement.cpp in Sources */,
27C6698C1C9585B80021E494 /* AbstractParseTreeVisitor.cpp in Sources */, 27C6698C1C9585B80021E494 /* AbstractParseTreeVisitor.cpp in Sources */,
27C669C01C9585B80021E494 /* Trees.cpp in Sources */, 27C669C01C9585B80021E494 /* Trees.cpp in Sources */,
27C66A351C958AC10021E494 /* XPath.cpp in Sources */,
278A66FC1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */, 278A66FC1C95838E002D667E /* ANTLRErrorListener.cpp in Sources */,
27C668391C95846E0021E494 /* RuleStopState.cpp in Sources */, 27C668391C95846E0021E494 /* RuleStopState.cpp in Sources */,
27C669AC1C9585B80021E494 /* RuleNode.cpp in Sources */, 27C669AC1C9585B80021E494 /* RuleNode.cpp in Sources */,
@ -1840,7 +1711,6 @@
27C6670B1C9584050021E494 /* NoViableAltException.cpp in Sources */, 27C6670B1C9584050021E494 /* NoViableAltException.cpp in Sources */,
27C666CF1C9584050021E494 /* CommonTokenFactory.cpp in Sources */, 27C666CF1C9584050021E494 /* CommonTokenFactory.cpp in Sources */,
27C667E31C95846E0021E494 /* BlockEndState.cpp in Sources */, 27C667E31C95846E0021E494 /* BlockEndState.cpp in Sources */,
27C66A3F1C958AC10021E494 /* XPathRuleElement.cpp in Sources */,
27C666E71C9584050021E494 /* FailedPredicateException.cpp in Sources */, 27C666E71C9584050021E494 /* FailedPredicateException.cpp in Sources */,
27C666C71C9584050021E494 /* CharStream.cpp in Sources */, 27C666C71C9584050021E494 /* CharStream.cpp in Sources */,
27C667A71C95846E0021E494 /* AbstractPredicateTransition.cpp in Sources */, 27C667A71C95846E0021E494 /* AbstractPredicateTransition.cpp in Sources */,
@ -1879,10 +1749,8 @@
276901AA1CAD7E67005CEC6A /* Recognizer.cpp in Sources */, 276901AA1CAD7E67005CEC6A /* Recognizer.cpp in Sources */,
27C667031C9584050021E494 /* LexerNoViableAltException.cpp in Sources */, 27C667031C9584050021E494 /* LexerNoViableAltException.cpp in Sources */,
27C666CB1C9584050021E494 /* CommonToken.cpp in Sources */, 27C666CB1C9584050021E494 /* CommonToken.cpp in Sources */,
27C66A431C958AC10021E494 /* XPathTokenElement.cpp in Sources */,
27C668311C95846E0021E494 /* RangeTransition.cpp in Sources */, 27C668311C95846E0021E494 /* RangeTransition.cpp in Sources */,
27C666E31C9584050021E494 /* Exceptions.cpp in Sources */, 27C666E31C9584050021E494 /* Exceptions.cpp in Sources */,
27C66A451C958AC10021E494 /* XPathWildcardAnywhereElement.cpp in Sources */,
27C667D71C95846E0021E494 /* AtomTransition.cpp in Sources */, 27C667D71C95846E0021E494 /* AtomTransition.cpp in Sources */,
27C668191C95846E0021E494 /* PlusLoopbackState.cpp in Sources */, 27C668191C95846E0021E494 /* PlusLoopbackState.cpp in Sources */,
27C667291C9584050021E494 /* Token.cpp in Sources */, 27C667291C9584050021E494 /* Token.cpp in Sources */,
@ -1896,13 +1764,11 @@
27C66A0B1C958AB30021E494 /* TagChunk.cpp in Sources */, 27C66A0B1C958AB30021E494 /* TagChunk.cpp in Sources */,
27C668AB1C9584FA0021E494 /* EqualityComparator.cpp in Sources */, 27C668AB1C9584FA0021E494 /* EqualityComparator.cpp in Sources */,
27C666FF1C9584050021E494 /* LexerInterpreter.cpp in Sources */, 27C666FF1C9584050021E494 /* LexerInterpreter.cpp in Sources */,
27C668C31C9584FA0021E494 /* LogManager.cpp in Sources */,
27C667FF1C95846E0021E494 /* LL1Analyzer.cpp in Sources */, 27C667FF1C95846E0021E494 /* LL1Analyzer.cpp in Sources */,
27C6673D1C9584050021E494 /* UnbufferedCharStream.cpp in Sources */, 27C6673D1C9584050021E494 /* UnbufferedCharStream.cpp in Sources */,
27C667D31C95846E0021E494 /* ATNType.cpp in Sources */, 27C667D31C95846E0021E494 /* ATNType.cpp in Sources */,
27C669B41C9585B80021E494 /* TerminalNode.cpp in Sources */, 27C669B41C9585B80021E494 /* TerminalNode.cpp in Sources */,
27C666C31C9584050021E494 /* BufferedTokenStream.cpp in Sources */, 27C666C31C9584050021E494 /* BufferedTokenStream.cpp in Sources */,
27C668C71C9584FA0021E494 /* MultiMap.cpp in Sources */,
27C666B71C9584050021E494 /* ANTLRInputStream.cpp in Sources */, 27C666B71C9584050021E494 /* ANTLRInputStream.cpp in Sources */,
27C668211C95846E0021E494 /* PredicateTransition.cpp in Sources */, 27C668211C95846E0021E494 /* PredicateTransition.cpp in Sources */,
27C667F71C95846E0021E494 /* LexerATNConfig.cpp in Sources */, 27C667F71C95846E0021E494 /* LexerATNConfig.cpp in Sources */,
@ -1914,18 +1780,15 @@
27C666DB1C9584050021E494 /* DefaultErrorStrategy.cpp in Sources */, 27C666DB1C9584050021E494 /* DefaultErrorStrategy.cpp in Sources */,
27C6690B1C9585230021E494 /* StringBuilder.cpp in Sources */, 27C6690B1C9585230021E494 /* StringBuilder.cpp in Sources */,
27C666F11C9584050021E494 /* InterpreterRuleContext.cpp in Sources */, 27C666F11C9584050021E494 /* InterpreterRuleContext.cpp in Sources */,
27C66A3D1C958AC10021E494 /* XPathRuleAnywhereElement.cpp in Sources */,
27C6672D1C9584050021E494 /* TokenFactory.cpp in Sources */, 27C6672D1C9584050021E494 /* TokenFactory.cpp in Sources */,
27C66A091C958AB30021E494 /* RuleTagToken.cpp in Sources */, 27C66A091C958AB30021E494 /* RuleTagToken.cpp in Sources */,
27C669051C9585230021E494 /* CPPUtils.cpp in Sources */, 27C669051C9585230021E494 /* CPPUtils.cpp in Sources */,
27C6671F1C9584050021E494 /* RecognitionException.cpp in Sources */, 27C6671F1C9584050021E494 /* RecognitionException.cpp in Sources */,
27C668111C95846E0021E494 /* ParserATNSimulator.cpp in Sources */, 27C668111C95846E0021E494 /* ParserATNSimulator.cpp in Sources */,
27C66A3B1C958AC10021E494 /* XPathLexerErrorListener.cpp in Sources */,
27C66A051C958AB30021E494 /* ParseTreePattern.cpp in Sources */, 27C66A051C958AB30021E494 /* ParseTreePattern.cpp in Sources */,
27C668FF1C9585230021E494 /* Arrays.cpp in Sources */, 27C668FF1C9585230021E494 /* Arrays.cpp in Sources */,
27C667E71C95846E0021E494 /* BlockStartState.cpp in Sources */, 27C667E71C95846E0021E494 /* BlockStartState.cpp in Sources */,
27C66A031C958AB30021E494 /* ParseTreeMatch.cpp in Sources */, 27C66A031C958AB30021E494 /* ParseTreeMatch.cpp in Sources */,
27C66A371C958AC10021E494 /* XPathElement.cpp in Sources */,
27C667CB1C95846E0021E494 /* ATNSimulator.cpp in Sources */, 27C667CB1C95846E0021E494 /* ATNSimulator.cpp in Sources */,
27C669901C9585B80021E494 /* ErrorNode.cpp in Sources */, 27C669901C9585B80021E494 /* ErrorNode.cpp in Sources */,
27C66A0D1C958AB30021E494 /* TextChunk.cpp in Sources */, 27C66A0D1C958AB30021E494 /* TextChunk.cpp in Sources */,
@ -1934,20 +1797,17 @@
27C669A01C9585B80021E494 /* ParseTreeProperty.cpp in Sources */, 27C669A01C9585B80021E494 /* ParseTreeProperty.cpp in Sources */,
27C668451C95846E0021E494 /* SetTransition.cpp in Sources */, 27C668451C95846E0021E494 /* SetTransition.cpp in Sources */,
27C667BB1C95846E0021E494 /* ATNConfigSet.cpp in Sources */, 27C667BB1C95846E0021E494 /* ATNConfigSet.cpp in Sources */,
27C668291C95846E0021E494 /* PredictionContextCache.cpp in Sources */,
27C668DF1C9584FA0021E494 /* TestRig.cpp in Sources */, 27C668DF1C9584FA0021E494 /* TestRig.cpp in Sources */,
27C668151C95846E0021E494 /* PlusBlockStartState.cpp in Sources */, 27C668151C95846E0021E494 /* PlusBlockStartState.cpp in Sources */,
27C6683D1C95846E0021E494 /* RuleTransition.cpp in Sources */, 27C6683D1C95846E0021E494 /* RuleTransition.cpp in Sources */,
27C6699C1C9585B80021E494 /* ParseTreeListener.cpp in Sources */, 27C6699C1C9585B80021E494 /* ParseTreeListener.cpp in Sources */,
27C6686E1C9584B60021E494 /* DFA.cpp in Sources */, 27C6686E1C9584B60021E494 /* DFA.cpp in Sources */,
27C666AF1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */, 27C666AF1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */,
27C668D71C9584FA0021E494 /* OrderedHashSet.cpp in Sources */,
27C667131C9584050021E494 /* ParserInterpreter.cpp in Sources */, 27C667131C9584050021E494 /* ParserInterpreter.cpp in Sources */,
27C669A41C9585B80021E494 /* ParseTreeVisitor.cpp in Sources */, 27C669A41C9585B80021E494 /* ParseTreeVisitor.cpp in Sources */,
2747A70B1CA691310030247B /* ConfigLookup.cpp in Sources */, 2747A70B1CA691310030247B /* ConfigLookup.cpp in Sources */,
27C667F31C95846E0021E494 /* EpsilonTransition.cpp in Sources */, 27C667F31C95846E0021E494 /* EpsilonTransition.cpp in Sources */,
27C667171C9584050021E494 /* ParserRuleContext.cpp in Sources */, 27C667171C9584050021E494 /* ParserRuleContext.cpp in Sources */,
27C66A471C958AC10021E494 /* XPathWildcardElement.cpp in Sources */,
27C667AB1C95846E0021E494 /* ActionTransition.cpp in Sources */, 27C667AB1C95846E0021E494 /* ActionTransition.cpp in Sources */,
27C668411C95846E0021E494 /* SemanticContext.cpp in Sources */, 27C668411C95846E0021E494 /* SemanticContext.cpp in Sources */,
27C668721C9584B60021E494 /* DFASerializer.cpp in Sources */, 27C668721C9584B60021E494 /* DFASerializer.cpp in Sources */,
@ -1966,10 +1826,8 @@
27C669101C9585230021E494 /* Strings.cpp in Sources */, 27C669101C9585230021E494 /* Strings.cpp in Sources */,
27C667241C9584050021E494 /* RuleContext.cpp in Sources */, 27C667241C9584050021E494 /* RuleContext.cpp in Sources */,
27C667FA1C95846E0021E494 /* LexerATNSimulator.cpp in Sources */, 27C667FA1C95846E0021E494 /* LexerATNSimulator.cpp in Sources */,
27C66A401C958AC10021E494 /* XPathTokenAnywhereElement.cpp in Sources */,
27C669AB1C9585B80021E494 /* RuleNode.cpp in Sources */, 27C669AB1C9585B80021E494 /* RuleNode.cpp in Sources */,
27C6670A1C9584050021E494 /* NoViableAltException.cpp in Sources */, 27C6670A1C9584050021E494 /* NoViableAltException.cpp in Sources */,
27C66A341C958AC10021E494 /* XPath.cpp in Sources */,
27C667161C9584050021E494 /* ParserRuleContext.cpp in Sources */, 27C667161C9584050021E494 /* ParserRuleContext.cpp in Sources */,
27C669BF1C9585B80021E494 /* Trees.cpp in Sources */, 27C669BF1C9585B80021E494 /* Trees.cpp in Sources */,
27C666B61C9584050021E494 /* ANTLRInputStream.cpp in Sources */, 27C666B61C9584050021E494 /* ANTLRInputStream.cpp in Sources */,
@ -1980,8 +1838,6 @@
27C669BB1C9585B80021E494 /* Tree.cpp in Sources */, 27C669BB1C9585B80021E494 /* Tree.cpp in Sources */,
27C6673C1C9584050021E494 /* UnbufferedCharStream.cpp in Sources */, 27C6673C1C9584050021E494 /* UnbufferedCharStream.cpp in Sources */,
27C6698B1C9585B80021E494 /* AbstractParseTreeVisitor.cpp in Sources */, 27C6698B1C9585B80021E494 /* AbstractParseTreeVisitor.cpp in Sources */,
27C66A3E1C958AC10021E494 /* XPathRuleElement.cpp in Sources */,
27C668281C95846E0021E494 /* PredictionContextCache.cpp in Sources */,
27C666D61C9584050021E494 /* ConsoleErrorListener.cpp in Sources */, 27C666D61C9584050021E494 /* ConsoleErrorListener.cpp in Sources */,
27C668381C95846E0021E494 /* RuleStopState.cpp in Sources */, 27C668381C95846E0021E494 /* RuleStopState.cpp in Sources */,
27C6680C1C95846E0021E494 /* OrderedATNConfigSet.cpp in Sources */, 27C6680C1C95846E0021E494 /* OrderedATNConfigSet.cpp in Sources */,
@ -2007,7 +1863,6 @@
27C666B21C9584050021E494 /* ANTLRFileStream.cpp in Sources */, 27C666B21C9584050021E494 /* ANTLRFileStream.cpp in Sources */,
27C668581C95846E0021E494 /* TokensStartState.cpp in Sources */, 27C668581C95846E0021E494 /* TokensStartState.cpp in Sources */,
27C668141C95846E0021E494 /* PlusBlockStartState.cpp in Sources */, 27C668141C95846E0021E494 /* PlusBlockStartState.cpp in Sources */,
27C668DA1C9584FA0021E494 /* ParseCancellationException.cpp in Sources */,
27C6672C1C9584050021E494 /* TokenFactory.cpp in Sources */, 27C6672C1C9584050021E494 /* TokenFactory.cpp in Sources */,
27C668081C95846E0021E494 /* NotSetTransition.cpp in Sources */, 27C668081C95846E0021E494 /* NotSetTransition.cpp in Sources */,
27C666CA1C9584050021E494 /* CommonToken.cpp in Sources */, 27C666CA1C9584050021E494 /* CommonToken.cpp in Sources */,
@ -2021,10 +1876,8 @@
276901A91CAD7E66005CEC6A /* Recognizer.cpp in Sources */, 276901A91CAD7E66005CEC6A /* Recognizer.cpp in Sources */,
27C669AF1C9585B80021E494 /* SyntaxTree.cpp in Sources */, 27C669AF1C9585B80021E494 /* SyntaxTree.cpp in Sources */,
27C667DA1C95846E0021E494 /* BasicBlockStartState.cpp in Sources */, 27C667DA1C95846E0021E494 /* BasicBlockStartState.cpp in Sources */,
27C66A421C958AC10021E494 /* XPathTokenElement.cpp in Sources */,
27C666AE1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */, 27C666AE1C9584050021E494 /* ANTLRErrorStrategy.cpp in Sources */,
27C667EA1C95846E0021E494 /* DecisionState.cpp in Sources */, 27C667EA1C95846E0021E494 /* DecisionState.cpp in Sources */,
27C66A441C958AC10021E494 /* XPathWildcardAnywhereElement.cpp in Sources */,
27C666FE1C9584050021E494 /* LexerInterpreter.cpp in Sources */, 27C666FE1C9584050021E494 /* LexerInterpreter.cpp in Sources */,
27C666CE1C9584050021E494 /* CommonTokenFactory.cpp in Sources */, 27C666CE1C9584050021E494 /* CommonTokenFactory.cpp in Sources */,
27C667381C9584050021E494 /* TokenStreamRewriter.cpp in Sources */, 27C667381C9584050021E494 /* TokenStreamRewriter.cpp in Sources */,
@ -2056,18 +1909,14 @@
27C667F21C95846E0021E494 /* EpsilonTransition.cpp in Sources */, 27C667F21C95846E0021E494 /* EpsilonTransition.cpp in Sources */,
27C669931C9585B80021E494 /* ErrorNodeImpl.cpp in Sources */, 27C669931C9585B80021E494 /* ErrorNodeImpl.cpp in Sources */,
27C666DA1C9584050021E494 /* DefaultErrorStrategy.cpp in Sources */, 27C666DA1C9584050021E494 /* DefaultErrorStrategy.cpp in Sources */,
27C66A3C1C958AC10021E494 /* XPathRuleAnywhereElement.cpp in Sources */,
27C667FE1C95846E0021E494 /* LL1Analyzer.cpp in Sources */, 27C667FE1C95846E0021E494 /* LL1Analyzer.cpp in Sources */,
27C6699B1C9585B80021E494 /* ParseTreeListener.cpp in Sources */, 27C6699B1C9585B80021E494 /* ParseTreeListener.cpp in Sources */,
27C66A081C958AB30021E494 /* RuleTagToken.cpp in Sources */, 27C66A081C958AB30021E494 /* RuleTagToken.cpp in Sources */,
27C667061C9584050021E494 /* ListTokenSource.cpp in Sources */, 27C667061C9584050021E494 /* ListTokenSource.cpp in Sources */,
27C6699F1C9585B80021E494 /* ParseTreeProperty.cpp in Sources */, 27C6699F1C9585B80021E494 /* ParseTreeProperty.cpp in Sources */,
27C668D61C9584FA0021E494 /* OrderedHashSet.cpp in Sources */,
27C66A3A1C958AC10021E494 /* XPathLexerErrorListener.cpp in Sources */,
27C66A041C958AB30021E494 /* ParseTreePattern.cpp in Sources */, 27C66A041C958AB30021E494 /* ParseTreePattern.cpp in Sources */,
27C6685C1C95846E0021E494 /* Transition.cpp in Sources */, 27C6685C1C95846E0021E494 /* Transition.cpp in Sources */,
27C66A021C958AB30021E494 /* ParseTreeMatch.cpp in Sources */, 27C66A021C958AB30021E494 /* ParseTreeMatch.cpp in Sources */,
27C66A361C958AC10021E494 /* XPathElement.cpp in Sources */,
27C668441C95846E0021E494 /* SetTransition.cpp in Sources */, 27C668441C95846E0021E494 /* SetTransition.cpp in Sources */,
27C668501C95846E0021E494 /* StarLoopbackState.cpp in Sources */, 27C668501C95846E0021E494 /* StarLoopbackState.cpp in Sources */,
27C666EC1C9584050021E494 /* InputMismatchException.cpp in Sources */, 27C666EC1C9584050021E494 /* InputMismatchException.cpp in Sources */,
@ -2084,14 +1933,11 @@
27C6690A1C9585230021E494 /* StringBuilder.cpp in Sources */, 27C6690A1C9585230021E494 /* StringBuilder.cpp in Sources */,
27C667341C9584050021E494 /* TokenStream.cpp in Sources */, 27C667341C9584050021E494 /* TokenStream.cpp in Sources */,
27C669141C9585230021E494 /* guid.cpp in Sources */, 27C669141C9585230021E494 /* guid.cpp in Sources */,
27C668C21C9584FA0021E494 /* LogManager.cpp in Sources */,
27C667281C9584050021E494 /* Token.cpp in Sources */, 27C667281C9584050021E494 /* Token.cpp in Sources */,
2747A70A1CA691310030247B /* ConfigLookup.cpp in Sources */, 2747A70A1CA691310030247B /* ConfigLookup.cpp in Sources */,
27C668791C9584B60021E494 /* LexerDFASerializer.cpp in Sources */, 27C668791C9584B60021E494 /* LexerDFASerializer.cpp in Sources */,
27C668601C95846E0021E494 /* WildcardTransition.cpp in Sources */, 27C668601C95846E0021E494 /* WildcardTransition.cpp in Sources */,
27C66A461C958AC10021E494 /* XPathWildcardElement.cpp in Sources */,
27C666E21C9584050021E494 /* Exceptions.cpp in Sources */, 27C666E21C9584050021E494 /* Exceptions.cpp in Sources */,
27C668C61C9584FA0021E494 /* MultiMap.cpp in Sources */,
27C668711C9584B60021E494 /* DFASerializer.cpp in Sources */, 27C668711C9584B60021E494 /* DFASerializer.cpp in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;

5
runtime/Cpp/demo/Test.g4 Normal file
View File

@ -0,0 +1,5 @@
grammar Test;
main: ID;
ID: [a..z]+;

View File

@ -25,7 +25,16 @@ set -o errexit
# This approach is especially useful if you are working on a target stg file, as it doesn't require to regenerate the # This approach is especially useful if you are working on a target stg file, as it doesn't require to regenerate the
# antlr jar over and over again. # antlr jar over and over again.
CLASSPATH=../../../tool/resources/:ST-4.0.8.jar:../../../tool/target/classes:../../../runtime/Java/target/classes:../../../../antlr3/runtime/Java/target/classes CLASSPATH=../../../tool/resources/:ST-4.0.8.jar:../../../tool/target/classes:../../../runtime/Java/target/classes:../../../../antlr3/runtime/Java/target/classes
# Minimal lexer + parser.
java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -no-listener -no-visitor -o generated/ -package antlrcpptest Test.g4
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Java -listener -visitor -o generated/ Test.g4
# A more complete lexer/parser set + listeners.
java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest TLexer.g4 TParser.g4 java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest TLexer.g4 TParser.g4
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest -XdbgST TLexer.g4 TParser.g4 #java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest -XdbgST TLexer.g4 TParser.g4
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest MySQL.g4
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Java -listener -visitor -o generated/ TLexer.g4 TParser.g4 #java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Java -listener -visitor -o generated/ TLexer.g4 TParser.g4
# A highly complex grammar.
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Cpp -listener -visitor -o generated/ -package antlrcpptest MySQL.g4
#java -cp $CLASSPATH org.antlr.v4.Tool -Dlanguage=Java -listener -visitor -o generated/ MySQL.g4

View File

@ -40,8 +40,7 @@ namespace antlr {
namespace v4 { namespace v4 {
namespace runtime { namespace runtime {
/// <summary> /// How to emit recognition errors (an interface in Java).
/// How to emit recognition errors. </summary>
class ANTLRErrorListener { class ANTLRErrorListener {
/// <summary> /// <summary>
@ -77,8 +76,8 @@ namespace 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. </param> /// surrounding rule. </param>
public: public:
void syntaxError(IRecognizer *recognizer, void *offendingSymbol, size_t line, int charPositionInLine, virtual void syntaxError(IRecognizer *recognizer, Token *offendingSymbol, size_t line, int charPositionInLine,
const std::wstring &msg, RecognitionException *e) {} const std::wstring &msg, RecognitionException *e) = 0;
/// <summary> /// <summary>
/// This method is called by the parser when a full-context prediction /// This method is called by the parser when a full-context prediction

View File

@ -51,13 +51,16 @@ namespace runtime {
/// Implementations of this interface report syntax errors by calling /// Implementations of this interface report syntax errors by calling
/// <seealso cref="Parser#notifyErrorListeners"/>. /// <seealso cref="Parser#notifyErrorListeners"/>.
/// <p/> /// <p/>
/// TODO: what to do about lexers /// TO_DO: what to do about lexers
/// </summary> /// </summary>
class ANTLRErrorStrategy { class ANTLRErrorStrategy {
public:
/// <summary> /// <summary>
/// Reset the error handler state for the specified {@code recognizer}. </summary> /// Reset the error handler state for the specified {@code recognizer}. </summary>
/// <param name="recognizer"> the parser instance </param> /// <param name="recognizer"> the parser instance </param>
public: virtual ~ANTLRErrorStrategy() {};
virtual void reset(Parser *recognizer) = 0; virtual void reset(Parser *recognizer) = 0;
/// <summary> /// <summary>

View File

@ -50,14 +50,14 @@ ANTLRInputStream::ANTLRInputStream(const wchar_t data[], size_t numberOfActualCh
: ANTLRInputStream(std::wstring(data, numberOfActualCharsInArray)) { : ANTLRInputStream(std::wstring(data, numberOfActualCharsInArray)) {
} }
ANTLRInputStream::ANTLRInputStream(std::wiostream &stream) : ANTLRInputStream(stream, READ_BUFFER_SIZE) { ANTLRInputStream::ANTLRInputStream(std::wistream &stream) : ANTLRInputStream(stream, READ_BUFFER_SIZE) {
} }
ANTLRInputStream::ANTLRInputStream(std::wiostream &stream, std::streamsize readChunkSize) : ANTLRInputStream() { ANTLRInputStream::ANTLRInputStream(std::wistream &stream, std::streamsize readChunkSize) : ANTLRInputStream() {
load(stream, readChunkSize); load(stream, readChunkSize);
} }
void ANTLRInputStream::load(std::wiostream &stream, std::streamsize readChunkSize) { void ANTLRInputStream::load(std::wistream &stream, std::streamsize readChunkSize) {
stream.seekg(0, stream.beg); stream.seekg(0, stream.beg);
if (!stream.good()) // No fail, bad or EOF. if (!stream.good()) // No fail, bad or EOF.
return; return;
@ -85,7 +85,7 @@ void ANTLRInputStream::reset() {
void ANTLRInputStream::consume() { void ANTLRInputStream::consume() {
if (p >= data.size()) { if (p >= data.size()) {
assert(LA(1) == IntStream::_EOF); assert(LA(1) == EOF);
throw IllegalStateException("cannot consume EOF"); throw IllegalStateException("cannot consume EOF");
} }
@ -94,7 +94,7 @@ void ANTLRInputStream::consume() {
} }
} }
size_t ANTLRInputStream::LA(ssize_t i) { ssize_t ANTLRInputStream::LA(ssize_t i) {
if (i == 0) { if (i == 0) {
return 0; // undefined return 0; // undefined
} }
@ -103,18 +103,18 @@ size_t ANTLRInputStream::LA(ssize_t i) {
if (i < 0) { if (i < 0) {
i++; // e.g., translate LA(-1) to use offset i=0; then data[p+0-1] i++; // e.g., translate LA(-1) to use offset i=0; then data[p+0-1]
if ((position + i - 1) < 0) { if ((position + i - 1) < 0) {
return IntStream::_EOF; // invalid; no char before first char return EOF; // invalid; no char before first char
} }
} }
if ((position + i - 1) >= (ssize_t)data.size()) { if ((position + i - 1) >= (ssize_t)data.size()) {
return IntStream::_EOF; return EOF;
} }
return (size_t)data[(size_t)(position + i - 1)]; return data[(size_t)(position + i - 1)];
} }
size_t ANTLRInputStream::LT(ssize_t i) { ssize_t ANTLRInputStream::LT(ssize_t i) {
return LA(i); return LA(i);
} }

View File

@ -57,18 +57,18 @@ namespace runtime {
ANTLRInputStream(const std::wstring &input = L""); ANTLRInputStream(const std::wstring &input = L"");
ANTLRInputStream(const wchar_t data[], size_t numberOfActualCharsInArray); ANTLRInputStream(const wchar_t data[], size_t numberOfActualCharsInArray);
ANTLRInputStream(std::wiostream &stream) ; ANTLRInputStream(std::wistream &stream);
ANTLRInputStream(std::wiostream &stream, std::streamsize readChunkSize); ANTLRInputStream(std::wistream &stream, std::streamsize readChunkSize);
virtual void load(std::wiostream &stream, std::streamsize readChunkSize); virtual void load(std::wistream &stream, std::streamsize readChunkSize);
/// 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
/// touched. /// touched.
virtual void reset(); virtual void reset();
virtual void consume() override; virtual void consume() override;
virtual size_t LA(ssize_t i) override; virtual ssize_t LA(ssize_t i) override;
virtual size_t LT(ssize_t i); virtual ssize_t LT(ssize_t i);
/// <summary> /// <summary>
/// Return the current input symbol index 0..n where n indicates the /// Return the current input symbol index 0..n where n indicates the

View File

@ -43,7 +43,7 @@ void BailErrorStrategy::recover(Parser *recognizer, RecognitionException *e) {
context->exception = e; context->exception = e;
} }
throw new ParseCancellationException(e); throw ParseCancellationException(e);
} }
Token *BailErrorStrategy::recoverInline(Parser *recognizer) { Token *BailErrorStrategy::recoverInline(Parser *recognizer) {
@ -55,7 +55,7 @@ Token *BailErrorStrategy::recoverInline(Parser *recognizer) {
context->exception = e; context->exception = e;
} }
throw new ParseCancellationException(e); throw ParseCancellationException(e);
} }

View File

@ -33,6 +33,10 @@
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
void BaseErrorListener::syntaxError(IRecognizer *recognizer, Token *offendingSymbol, size_t line, int charPositionInLine,
const std::wstring &msg, RecognitionException *e) {
}
void BaseErrorListener::reportAmbiguity(Parser *recognizer, dfa::DFA *dfa, size_t startIndex, size_t stopIndex, void BaseErrorListener::reportAmbiguity(Parser *recognizer, dfa::DFA *dfa, size_t startIndex, size_t stopIndex,
bool exact, antlrcpp::BitSet *ambigAlts, atn::ATNConfigSet *configs) { bool exact, antlrcpp::BitSet *ambigAlts, atn::ATNConfigSet *configs) {
} }

View File

@ -44,8 +44,8 @@ namespace runtime {
class BaseErrorListener : public ANTLRErrorListener { class BaseErrorListener : public ANTLRErrorListener {
void syntaxError(IRecognizer *recognizer, void *offendingSymbol, size_t line, int charPositionInLine, virtual void syntaxError(IRecognizer *recognizer, Token *offendingSymbol, size_t line, int charPositionInLine,
const std::wstring &msg, RecognitionException *e) { } const std::wstring &msg, RecognitionException *e) override;
virtual void reportAmbiguity(Parser *recognizer, dfa::DFA *dfa, size_t startIndex, size_t stopIndex, bool exact, virtual void reportAmbiguity(Parser *recognizer, dfa::DFA *dfa, size_t startIndex, size_t stopIndex, bool exact,
antlrcpp::BitSet *ambigAlts, atn::ATNConfigSet *configs) override; antlrcpp::BitSet *ambigAlts, atn::ATNConfigSet *configs) override;

View File

@ -43,7 +43,7 @@ using namespace org::antlr::v4::runtime;
BufferedTokenStream::BufferedTokenStream(TokenSource *tokenSource) { BufferedTokenStream::BufferedTokenStream(TokenSource *tokenSource) {
InitializeInstanceFields(); InitializeInstanceFields();
if (tokenSource == nullptr) { if (tokenSource == nullptr) {
throw new NullPointerException("tokenSource cannot be null"); throw NullPointerException("tokenSource cannot be null");
} }
this->tokenSource = tokenSource; this->tokenSource = tokenSource;
} }
@ -78,8 +78,8 @@ size_t BufferedTokenStream::size() {
} }
void BufferedTokenStream::consume() { void BufferedTokenStream::consume() {
if (LA(1) == _EOF) { if (LA(1) == EOF) {
throw new IllegalStateException("cannot consume EOF"); throw IllegalStateException("cannot consume EOF");
} }
if (sync(p + 1)) { if (sync(p + 1)) {
@ -109,7 +109,7 @@ size_t BufferedTokenStream::fetch(size_t n) {
(static_cast<WritableToken*>(t))->setTokenIndex((int)tokens.size()); (static_cast<WritableToken*>(t))->setTokenIndex((int)tokens.size());
} }
tokens.push_back(t); tokens.push_back(t);
if (t->getType() == Token::_EOF) { if (t->getType() == EOF) {
fetchedEOF = true; fetchedEOF = true;
return i + 1; return i + 1;
} }
@ -142,7 +142,7 @@ std::vector<Token*> BufferedTokenStream::get(size_t start, size_t stop) {
} }
for (size_t i = start; i <= stop; i++) { for (size_t i = start; i <= stop; i++) {
Token *t = tokens[i]; Token *t = tokens[i];
if (t->getType() == Token::_EOF) { if (t->getType() == EOF) {
break; break;
} }
subset.push_back(t); subset.push_back(t);
@ -150,8 +150,8 @@ std::vector<Token*> BufferedTokenStream::get(size_t start, size_t stop) {
return subset; return subset;
} }
size_t BufferedTokenStream::LA(ssize_t i) { ssize_t BufferedTokenStream::LA(ssize_t i) {
return (size_t)LT(i)->getType(); return LT(i)->getType();
} }
Token *BufferedTokenStream::LB(size_t k) { Token *BufferedTokenStream::LB(size_t k) {
@ -213,7 +213,7 @@ std::vector<Token*> BufferedTokenStream::getTokens(int start, int stop) {
std::vector<Token*> BufferedTokenStream::getTokens(int start, int stop, std::vector<int> *types) { std::vector<Token*> BufferedTokenStream::getTokens(int start, int stop, std::vector<int> *types) {
lazyInit(); lazyInit();
if (start < 0 || stop >= (int)tokens.size() || stop < 0 || (int)start >= (int)tokens.size()) { if (start < 0 || stop >= (int)tokens.size() || stop < 0 || (int)start >= (int)tokens.size()) {
throw new IndexOutOfBoundsException(std::string("start ") + throw IndexOutOfBoundsException(std::string("start ") +
std::to_string(start) + std::to_string(start) +
std::string(" or stop ") + std::string(" or stop ") +
std::to_string(stop) + std::to_string(stop) +
@ -257,7 +257,7 @@ ssize_t BufferedTokenStream::nextTokenOnChannel(size_t i, int channel) {
Token *token = tokens[i]; Token *token = tokens[i];
while (token->getChannel() != channel) { while (token->getChannel() != channel) {
if (token->getType() == Token::_EOF) { if (token->getType() == EOF) {
return -1; return -1;
} }
i++; i++;
@ -281,9 +281,7 @@ ssize_t BufferedTokenStream::previousTokenOnChannel(size_t i, int channel) const
std::vector<Token*> BufferedTokenStream::getHiddenTokensToRight(size_t tokenIndex, int channel) { std::vector<Token*> BufferedTokenStream::getHiddenTokensToRight(size_t tokenIndex, int channel) {
lazyInit(); lazyInit();
if (tokenIndex >= tokens.size()) { if (tokenIndex >= tokens.size()) {
throw new IndexOutOfBoundsException(std::to_string(tokenIndex) + throw IndexOutOfBoundsException(std::to_string(tokenIndex) + " not in 0.." + std::to_string(tokens.size() - 1));
std::string(" not in 0..") +
std::to_string(tokens.size() - 1));
} }
ssize_t nextOnChannel = nextTokenOnChannel(tokenIndex + 1, Lexer::DEFAULT_TOKEN_CHANNEL); ssize_t nextOnChannel = nextTokenOnChannel(tokenIndex + 1, Lexer::DEFAULT_TOKEN_CHANNEL);
@ -306,9 +304,7 @@ std::vector<Token*> BufferedTokenStream::getHiddenTokensToRight(size_t tokenInde
std::vector<Token*> BufferedTokenStream::getHiddenTokensToLeft(size_t tokenIndex, int channel) { std::vector<Token*> BufferedTokenStream::getHiddenTokensToLeft(size_t tokenIndex, int channel) {
lazyInit(); lazyInit();
if (tokenIndex >= tokens.size()) { if (tokenIndex >= tokens.size()) {
throw new IndexOutOfBoundsException(std::to_string(tokenIndex) + throw IndexOutOfBoundsException(std::to_string(tokenIndex) + " not in 0.." + std::to_string(tokens.size() - 1));
std::string(" not in 0..") +
std::to_string(tokens.size() - 1));
} }
ssize_t prevOnChannel = previousTokenOnChannel(tokenIndex - 1, Lexer::DEFAULT_TOKEN_CHANNEL); ssize_t prevOnChannel = previousTokenOnChannel(tokenIndex - 1, Lexer::DEFAULT_TOKEN_CHANNEL);
@ -374,7 +370,7 @@ std::wstring BufferedTokenStream::getText(const misc::Interval &interval) {
antlrcpp::StringBuilder *buf = new antlrcpp::StringBuilder(); antlrcpp::StringBuilder *buf = new antlrcpp::StringBuilder();
for (size_t i = (size_t)start; i <= (size_t)stop; i++) { for (size_t i = (size_t)start; i <= (size_t)stop; i++) {
Token *t = tokens[i]; Token *t = tokens[i];
if (t->getType() == Token::_EOF) { if (t->getType() == EOF) {
break; break;
} }
buf->append(t->getText()); buf->append(t->getText());

View File

@ -118,7 +118,7 @@ namespace runtime {
/// Get all tokens from start..stop inclusively </summary> /// Get all tokens from start..stop inclusively </summary>
virtual std::vector<Token*> get(size_t start, size_t stop); virtual std::vector<Token*> get(size_t start, size_t stop);
virtual size_t LA(ssize_t i) override; virtual ssize_t LA(ssize_t i) override;
protected: protected:
virtual Token *LB(size_t k); virtual Token *LB(size_t k);

View File

@ -169,25 +169,6 @@ org::antlr::v4::runtime::CharStream *CommonToken::getInputStream() {
return source->second; return source->second;
} }
std::wstring CommonToken::toString() {
std::wstring channelStr = L"";
if (channel > 0) {
channelStr = std::wstring(L",channel=") + std::to_wstring(channel);
}
std::wstring txt = getText();
if (txt != L"") {
antlrcpp::replaceAll(txt, L"\n",L"\\n");
antlrcpp::replaceAll(txt, L"\r",L"\\r");
antlrcpp::replaceAll(txt, L"\t",L"\\t");
} else {
txt = L"<no text>";
}
return std::wstring(L"[@") + std::to_wstring(getTokenIndex()) + std::wstring(L",") + std::to_wstring(start) + std::wstring(L":") + std::to_wstring(stop) + std::wstring(L"='") + txt + std::wstring(L"',<") + std::to_wstring(type) + std::wstring(L">") + channelStr + std::wstring(L",") + std::to_wstring(line) + std::wstring(L":") + std::to_wstring(getCharPositionInLine()) + std::wstring(L"]");
}
void CommonToken::InitializeInstanceFields() { void CommonToken::InitializeInstanceFields() {
type = 0; type = 0;
line = 0; line = 0;

View File

@ -53,7 +53,7 @@ namespace runtime {
/// this is non-empty, then getText should return this. Note that /// this is non-empty, then getText should return this. Note that
/// start/stop are not affected by changing this. /// start/stop are not affected by changing this.
/// </summary> /// </summary>
// TODO: can store these in map in token stream rather than as field here // TO_DO: can store these in map in token stream rather than as field here
std::wstring text; std::wstring text;
/// <summary> /// <summary>
@ -119,8 +119,6 @@ namespace runtime {
virtual CharStream *getInputStream() override; virtual CharStream *getInputStream() override;
virtual std::wstring toString() ;
private: private:
void InitializeInstanceFields(); void InitializeInstanceFields();
}; };

View File

@ -96,7 +96,7 @@ int CommonTokenStream::getNumberOfOnChannelTokens() {
if (t->getChannel() == channel) { if (t->getChannel() == channel) {
n++; n++;
} }
if (t->getType() == Token::_EOF) { if (t->getType() == EOF) {
break; break;
} }
} }

View File

@ -120,10 +120,10 @@ void DefaultErrorStrategy::sync(Parser *recognizer) {
} }
TokenStream *tokens = recognizer->getInputStream(); TokenStream *tokens = recognizer->getInputStream();
size_t la = tokens->LA(1); ssize_t 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->getATN().nextTokens(s).contains((int)la) || la == Token::_EOF) { if (recognizer->getATN().nextTokens(s).contains((int)la) || la == EOF) {
return; return;
} }
@ -142,7 +142,7 @@ void DefaultErrorStrategy::sync(Parser *recognizer) {
return; return;
} }
throw new InputMismatchException(recognizer); throw InputMismatchException(recognizer);
case atn::ATNState::PLUS_LOOP_BACK: case atn::ATNState::PLUS_LOOP_BACK:
case atn::ATNState::STAR_LOOP_BACK: { case atn::ATNState::STAR_LOOP_BACK: {
@ -164,7 +164,7 @@ void DefaultErrorStrategy::reportNoViableAlternative(Parser *recognizer, NoViabl
TokenStream *tokens = recognizer->getInputStream(); TokenStream *tokens = recognizer->getInputStream();
std::wstring input; std::wstring input;
if (tokens != nullptr) { if (tokens != nullptr) {
if (e->getStartToken()->getType() == Token::_EOF) { if (e->getStartToken()->getType() == EOF) {
input = L"<EOF>"; input = L"<EOF>";
} else { } else {
input = tokens->getText(e->getStartToken().get(), e->getOffendingToken().get()); input = tokens->getText(e->getStartToken().get(), e->getOffendingToken().get());
@ -236,7 +236,7 @@ Token *DefaultErrorStrategy::recoverInline(Parser *recognizer) {
} }
bool DefaultErrorStrategy::singleTokenInsertion(Parser *recognizer) { bool DefaultErrorStrategy::singleTokenInsertion(Parser *recognizer) {
size_t currentSymbolType = recognizer->getInputStream()->LA(1); ssize_t currentSymbolType = recognizer->getInputStream()->LA(1);
// if current token is consistent with what could come after current // if current token is consistent with what could come after current
// ATN state, then we know we're missing a token; error recovery // ATN state, then we know we're missing a token; error recovery
@ -253,7 +253,7 @@ bool DefaultErrorStrategy::singleTokenInsertion(Parser *recognizer) {
} }
Token *DefaultErrorStrategy::singleTokenDeletion(Parser *recognizer) { Token *DefaultErrorStrategy::singleTokenDeletion(Parser *recognizer) {
size_t nextTokenType = recognizer->getInputStream()->LA(2); ssize_t nextTokenType = recognizer->getInputStream()->LA(2);
misc::IntervalSet expecting = getExpectedTokens(recognizer); misc::IntervalSet expecting = getExpectedTokens(recognizer);
if (expecting.contains((int)nextTokenType)) { if (expecting.contains((int)nextTokenType)) {
reportUnwantedToken(recognizer); reportUnwantedToken(recognizer);
@ -269,16 +269,16 @@ Token *DefaultErrorStrategy::singleTokenDeletion(Parser *recognizer) {
Token *DefaultErrorStrategy::getMissingSymbol(Parser *recognizer) { Token *DefaultErrorStrategy::getMissingSymbol(Parser *recognizer) {
Token *currentSymbol = recognizer->getCurrentToken(); Token *currentSymbol = recognizer->getCurrentToken();
misc::IntervalSet expecting = getExpectedTokens(recognizer); misc::IntervalSet expecting = getExpectedTokens(recognizer);
size_t expectedTokenType = (size_t)expecting.getMinElement(); // get any element ssize_t expectedTokenType = expecting.getMinElement(); // get any element
std::wstring tokenText; std::wstring tokenText;
if (expectedTokenType == Token::_EOF) { if (expectedTokenType == EOF) {
tokenText = L"<missing EOF>"; tokenText = L"<missing EOF>";
} else { } else {
tokenText = std::wstring(L"<missing ") + recognizer->getTokenNames()[expectedTokenType][expectedTokenType] + std::wstring(L">"); tokenText = std::wstring(L"<missing ") + recognizer->getTokenNames()[(size_t)expectedTokenType] + std::wstring(L">");
} }
Token *current = currentSymbol; Token *current = currentSymbol;
Token *lookback = recognizer->getInputStream()->LT(-1); Token *lookback = recognizer->getInputStream()->LT(-1);
if (current->getType() == Token::_EOF && lookback != nullptr) { if (current->getType() == EOF && lookback != nullptr) {
current = lookback; current = lookback;
} }
return (Token*)recognizer->getTokenFactory()->create(new std::pair<TokenSource*, CharStream*>(current->getTokenSource(), return (Token*)recognizer->getTokenFactory()->create(new std::pair<TokenSource*, CharStream*>(current->getTokenSource(),
@ -296,7 +296,7 @@ std::wstring DefaultErrorStrategy::getTokenErrorDisplay(Token *t) {
} }
std::wstring s = getSymbolText(t); std::wstring s = getSymbolText(t);
if (s == L"") { if (s == L"") {
if (getSymbolType(t) == Token::_EOF) { if (getSymbolType(t) == EOF) {
s = L"<EOF>"; s = L"<EOF>";
} else { } else {
s = std::wstring(L"<") + std::to_wstring(getSymbolType(t)) + std::wstring(L">"); s = std::wstring(L"<") + std::to_wstring(getSymbolType(t)) + std::wstring(L">");
@ -339,8 +339,8 @@ misc::IntervalSet DefaultErrorStrategy::getErrorRecoverySet(Parser *recognizer)
} }
void DefaultErrorStrategy::consumeUntil(Parser *recognizer, const misc::IntervalSet &set) { void DefaultErrorStrategy::consumeUntil(Parser *recognizer, const misc::IntervalSet &set) {
size_t ttype = recognizer->getInputStream()->LA(1); ssize_t ttype = recognizer->getInputStream()->LA(1);
while (ttype != Token::_EOF && !set.contains((int)ttype)) { while (ttype != EOF && !set.contains((int)ttype)) {
recognizer->consume(); recognizer->consume();
ttype = recognizer->getInputStream()->LA(1); ttype = recognizer->getInputStream()->LA(1);
} }

View File

@ -81,6 +81,12 @@ namespace runtime {
UnsupportedOperationException(const std::string &msg, RuntimeException *cause = nullptr) : RuntimeException(msg, cause) {}; UnsupportedOperationException(const std::string &msg, RuntimeException *cause = nullptr) : RuntimeException(msg, cause) {};
}; };
class EmptyStackException : public RuntimeException {
public:
EmptyStackException(RuntimeException *cause = nullptr) : EmptyStackException("", cause) {};
EmptyStackException(const std::string &msg, RuntimeException *cause = nullptr) : RuntimeException(msg, cause) {};
};
// IOException is not a runtime exception (in the java hierarchy). // IOException is not a runtime exception (in the java hierarchy).
// Hence we have to duplicate the RuntimeException implementation. // Hence we have to duplicate the RuntimeException implementation.
class IOException : public std::exception { class IOException : public std::exception {
@ -98,6 +104,18 @@ namespace runtime {
virtual const char* what() const noexcept override; virtual const char* what() const noexcept override;
}; };
class CancellationException : public IllegalStateException {
public:
CancellationException(RuntimeException *cause = nullptr) : CancellationException("", cause) {};
CancellationException(const std::string &msg, RuntimeException *cause = nullptr) : IllegalStateException(msg, cause) {};
};
class ParseCancellationException : public CancellationException {
public:
ParseCancellationException(RuntimeException *cause = nullptr) : ParseCancellationException("", cause) {};
ParseCancellationException(const std::string &msg, RuntimeException *cause = nullptr) : CancellationException(msg, cause) {};
};
} // namespace runtime } // namespace runtime
} // namespace v4 } // namespace v4
} // namespace antlr } // namespace antlr

View File

@ -53,13 +53,11 @@ namespace runtime {
/// </ul> /// </ul>
/// </summary> /// </summary>
class IntStream { class IntStream {
/// <summary> public:
/// The value returned by <seealso cref="#LA LA()"/> when the end of the stream is /// The value returned by <seealso cref="#LA LA()"/> when the end of the stream is
/// reached. /// reached.
/// </summary> /// No explicit EOF definition. We got EOF on all platforms.
public: //static const size_t _EOF = std::ios::eofbit;
// EOF Conflict with OS X, change to _EOF
static const size_t _EOF = std::ios::eofbit;
/// <summary> /// <summary>
/// The value returned by <seealso cref="#getSourceName"/> when the actual name of the /// The value returned by <seealso cref="#getSourceName"/> when the actual name of the
@ -123,7 +121,7 @@ namespace runtime {
/// </summary> /// </summary>
/// <exception cref="UnsupportedOperationException"> if the stream does not support /// <exception cref="UnsupportedOperationException"> if the stream does not support
/// retrieving the value of the specified symbol </exception> /// retrieving the value of the specified symbol </exception>
virtual size_t LA(ssize_t i) = 0; virtual ssize_t LA(ssize_t i) = 0;
/// <summary> /// <summary>
/// A mark provides a guarantee that <seealso cref="#seek seek()"/> operations will be /// A mark provides a guarantee that <seealso cref="#seek seek()"/> operations will be

View File

@ -37,9 +37,11 @@
#include "stringconverter.h" #include "stringconverter.h"
#include "StringBuilder.h" #include "StringBuilder.h"
#include "ANTLRErrorListener.h" #include "ANTLRErrorListener.h"
#include "CPPUtils.h"
#include "Lexer.h" #include "Lexer.h"
using namespace antlrcpp;
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
Lexer::Lexer() { Lexer::Lexer() {
@ -74,13 +76,19 @@ void Lexer::reset() {
Token *Lexer::nextToken() { Token *Lexer::nextToken() {
if (_input == nullptr) { if (_input == nullptr) {
throw new IllegalStateException("nextToken requires a non-null input stream."); throw IllegalStateException("nextToken requires a non-null input stream.");
} }
// Mark start location in char stream so unbuffered streams are // Mark start location in char stream so unbuffered streams are
// guaranteed at least have text of current token // guaranteed at least have text of current token
ssize_t tokenStartMarker = _input->mark(); ssize_t tokenStartMarker = _input->mark();
try {
auto onExit = finally([this, tokenStartMarker]{
// make sure we release marker after match or
// unbuffered char stream will keep buffering
_input->release(tokenStartMarker);
});
while (true) { while (true) {
outerContinue: outerContinue:
if (_hitEOF) { if (_hitEOF) {
@ -89,6 +97,7 @@ Token *Lexer::nextToken() {
} }
delete _token; delete _token;
_token = nullptr;
_channel = Token::DEFAULT_CHANNEL; _channel = Token::DEFAULT_CHANNEL;
_tokenStartCharIndex = (int)_input->index(); _tokenStartCharIndex = (int)_input->index();
_tokenStartCharPositionInLine = getInterpreter<atn::LexerATNSimulator>()->getCharPositionInLine(); _tokenStartCharPositionInLine = getInterpreter<atn::LexerATNSimulator>()->getCharPositionInLine();
@ -104,7 +113,7 @@ Token *Lexer::nextToken() {
recover(e); recover(e);
ttype = SKIP; ttype = SKIP;
} }
if (_input->LA(1) == IntStream::_EOF) { if (_input->LA(1) == EOF) {
_hitEOF = true; _hitEOF = true;
} }
if (_type == Token::INVALID_TYPE) { if (_type == Token::INVALID_TYPE) {
@ -119,18 +128,6 @@ Token *Lexer::nextToken() {
} }
return _token; return _token;
} }
}
catch(...) {
#ifdef TODO
// Do something intelligent here for once
#endif
}
// make sure we release marker after match or
// unbuffered char stream will keep buffering
_input->release(tokenStartMarker);
return nullptr;
} }
void Lexer::skip() { void Lexer::skip() {
@ -205,7 +202,7 @@ Token *Lexer::emitEOF() {
int n = _token->getStopIndex() - _token->getStartIndex() + 1; int n = _token->getStopIndex() - _token->getStartIndex() + 1;
cpos = _token->getCharPositionInLine() + n; cpos = _token->getCharPositionInLine() + n;
} }
Token *eof = (Token*)_factory->create(_tokenFactorySourcePair, Token::_EOF, L"", Token::DEFAULT_CHANNEL, Token *eof = (Token*)_factory->create(_tokenFactorySourcePair, EOF, L"", Token::DEFAULT_CHANNEL,
(int)_input->index(), (int)_input->index() - 1, (int)getLine(), cpos); (int)_input->index(), (int)_input->index() - 1, (int)getLine(), cpos);
emit(eof); emit(eof);
return eof; return eof;
@ -269,7 +266,7 @@ int Lexer::getChannel() {
std::vector<Token*> Lexer::getAllTokens() { std::vector<Token*> Lexer::getAllTokens() {
std::vector<Token*> tokens = std::vector<Token*>(); std::vector<Token*> tokens = std::vector<Token*>();
Token *t = nextToken(); Token *t = nextToken();
while (t->getType() != Token::_EOF) { while (t->getType() != EOF) {
tokens.push_back(t); tokens.push_back(t);
t = nextToken(); t = nextToken();
} }
@ -277,7 +274,7 @@ std::vector<Token*> Lexer::getAllTokens() {
} }
void Lexer::recover(LexerNoViableAltException *e) { void Lexer::recover(LexerNoViableAltException *e) {
if (_input->LA(1) != IntStream::_EOF) { if (_input->LA(1) != EOF) {
// skip a char and try again // skip a char and try again
getInterpreter<atn::LexerATNSimulator>()->consume(_input); getInterpreter<atn::LexerATNSimulator>()->consume(_input);
} }
@ -309,7 +306,7 @@ std::wstring Lexer::getErrorDisplay(const std::wstring &s) {
std::wstring Lexer::getErrorDisplay(int c) { std::wstring Lexer::getErrorDisplay(int c) {
std::wstring s = antlrcpp::StringConverterHelper::toString(static_cast<wchar_t>(c)); std::wstring s = antlrcpp::StringConverterHelper::toString(static_cast<wchar_t>(c));
switch (c) { switch (c) {
case Token::_EOF : case EOF :
s = L"<EOF>"; s = L"<EOF>";
break; break;
case L'\n' : case L'\n' :
@ -331,7 +328,7 @@ std::wstring Lexer::getCharErrorDisplay(int c) {
} }
void Lexer::recover(RecognitionException *re) { void Lexer::recover(RecognitionException *re) {
// TODO: Do we lose character or line position information? // TO_DO: Do we lose character or line position information?
_input->consume(); _input->consume();
} }

View File

@ -32,7 +32,6 @@
#include "ATNType.h" #include "ATNType.h"
#include "LexerATNSimulator.h" #include "LexerATNSimulator.h"
#include "DFA.h" #include "DFA.h"
#include "PredictionContextCache.h"
#include "EmptyPredictionContext.h" #include "EmptyPredictionContext.h"
#include "Exceptions.h" #include "Exceptions.h"
@ -43,7 +42,7 @@ using namespace org::antlr::v4::runtime;
LexerInterpreter::LexerInterpreter(const std::wstring &grammarFileName, std::vector<std::wstring> *tokenNames, std::vector<std::wstring> *ruleNames, std::vector<std::wstring> *modeNames, const atn::ATN &atn, CharStream *input) : Lexer(input), grammarFileName(grammarFileName), _atn(atn), _sharedContextCache(new atn::PredictionContextCache()) { LexerInterpreter::LexerInterpreter(const std::wstring &grammarFileName, std::vector<std::wstring> *tokenNames, std::vector<std::wstring> *ruleNames, std::vector<std::wstring> *modeNames, const atn::ATN &atn, CharStream *input) : Lexer(input), grammarFileName(grammarFileName), _atn(atn), _sharedContextCache(new atn::PredictionContextCache()) {
if (_atn.grammarType != atn::ATNType::LEXER) { if (_atn.grammarType != atn::ATNType::LEXER) {
throw new IllegalArgumentException("The ATN must be a lexer ATN."); throw IllegalArgumentException("The ATN must be a lexer ATN.");
} }

View File

@ -48,7 +48,7 @@ namespace runtime {
std::vector<std::wstring> _modeNames; std::vector<std::wstring> _modeNames;
std::vector<dfa::DFA*> _decisionToDFA; std::vector<dfa::DFA*> _decisionToDFA;
atn::PredictionContextCache *const _sharedContextCache; std::shared_ptr<atn::PredictionContextCache> _sharedContextCache;
public: public:
LexerInterpreter(const std::wstring &grammarFileName, std::vector<std::wstring> *tokenNames, std::vector<std::wstring> *ruleNames, std::vector<std::wstring> *modeNames, const atn::ATN &atn, CharStream *input); LexerInterpreter(const std::wstring &grammarFileName, std::vector<std::wstring> *tokenNames, std::vector<std::wstring> *ruleNames, std::vector<std::wstring> *modeNames, const atn::ATN &atn, CharStream *input);

View File

@ -74,7 +74,7 @@ Token *ListTokenSource::nextToken() {
} }
int stop = std::max(-1, start - 1); int stop = std::max(-1, start - 1);
eofToken = _factory->create(new std::pair<TokenSource*, CharStream*>(this, getInputStream()), Token::_EOF, eofToken = _factory->create(new std::pair<TokenSource*, CharStream*>(this, getInputStream()), EOF,
L"EOF", Token::DEFAULT_CHANNEL, start, stop, (int)getLine(), getCharPositionInLine()); L"EOF", Token::DEFAULT_CHANNEL, start, stop, (int)getLine(), getCharPositionInLine());
} }
@ -82,7 +82,7 @@ Token *ListTokenSource::nextToken() {
} }
Token *t = tokens[i]; Token *t = tokens[i];
if (i == tokens.size() - 1 && t->getType() == Token::_EOF) { if (i == tokens.size() - 1 && t->getType() == EOF) {
eofToken = t; eofToken = t;
} }

View File

@ -91,18 +91,17 @@ void Parser::TrimToSizeListener::visitErrorNode(tree::ErrorNode *node) {
} }
void Parser::TrimToSizeListener::exitEveryRule(ParserRuleContext *ctx) { void Parser::TrimToSizeListener::exitEveryRule(ParserRuleContext *ctx) {
// TODO: Need to figure out what type this is going to be. In Java we expect it to be set by the generator. ctx->children.shrink_to_fit();
std::vector<tree::ParseTree*>* tmp = dynamic_cast<std::vector<tree::ParseTree*>*>(&ctx->_children);
if (tmp != nullptr) {
tmp->shrink_to_fit();
}
} }
Parser::Parser(TokenStream* input) { Parser::Parser(TokenStream* input) : _tracer(this) {
InitializeInstanceFields(); InitializeInstanceFields();
setInputStream(input); setInputStream(input);
} }
Parser::~Parser() {
}
void Parser::reset() { void Parser::reset() {
if (getInputStream() != nullptr) { if (getInputStream() != nullptr) {
getInputStream()->seek(0); getInputStream()->seek(0);
@ -274,12 +273,12 @@ tree::pattern::ParseTreePattern *Parser::compileParseTreePattern(const std::wstr
return m->compile(pattern, patternRuleIndex); return m->compile(pattern, patternRuleIndex);
} }
ANTLRErrorStrategy *Parser::getErrorHandler() { std::shared_ptr<ANTLRErrorStrategy> Parser::getErrorHandler() {
return _errHandler; return _errHandler;
} }
void Parser::setErrorHandler(ANTLRErrorStrategy *handler) { void Parser::setErrorHandler(std::shared_ptr<ANTLRErrorStrategy> handler) {
this->_errHandler = handler; _errHandler = handler;
} }
TokenStream *Parser::getInputStream() { TokenStream *Parser::getInputStream() {
@ -468,7 +467,7 @@ bool Parser::precpred(RuleContext *localctx, int precedence) {
} }
bool Parser::inContext(const std::wstring &context) { bool Parser::inContext(const std::wstring &context) {
// TODO: useful in parser? // TO_DO: useful in parser?
return false; return false;
} }
@ -497,7 +496,7 @@ bool Parser::isExpectedToken(int symbol) {
ctx = static_cast<ParserRuleContext*>(ctx->parent); ctx = static_cast<ParserRuleContext*>(ctx->parent);
} }
if (following.contains(Token::EPSILON) && symbol == Token::_EOF) { if (following.contains(Token::EPSILON) && symbol == EOF) {
return true; return true;
} }
@ -587,22 +586,15 @@ std::string Parser::getSourceName() {
void Parser::setTrace(bool trace) { void Parser::setTrace(bool trace) {
if (!trace) { if (!trace) {
removeParseListener(_tracer); removeParseListener(&_tracer);
// TODO
//JAVA TO C++ CONVERTER WARNING: Java to C++ Converter converted the original 'null' assignment to a call to 'delete', but you should review memory allocation of all pointer variables in the converted code:
delete _tracer;
} else { } else {
if (_tracer != nullptr) { removeParseListener(&_tracer); // Just in case this is triggered multiple times.
removeParseListener(_tracer); addParseListener(&_tracer);
} else {
_tracer = new TraceListener(this);
}
addParseListener(_tracer);
} }
} }
void Parser::InitializeInstanceFields() { void Parser::InitializeInstanceFields() {
_errHandler = new DefaultErrorStrategy(); _errHandler.reset(new DefaultErrorStrategy());
_precedenceStack.clear(); _precedenceStack.clear();
_precedenceStack.push_back(0); _precedenceStack.push_back(0);
_buildParseTrees = true; _buildParseTrees = true;

View File

@ -77,6 +77,7 @@ namespace runtime {
ParserRuleContext *ctx; ParserRuleContext *ctx;
Parser(TokenStream *input); Parser(TokenStream *input);
virtual ~Parser();
/// <summary> /// <summary>
/// reset the parser's state </summary> /// reset the parser's state </summary>
@ -256,9 +257,8 @@ namespace runtime {
/// </summary> /// </summary>
virtual tree::pattern::ParseTreePattern *compileParseTreePattern(const std::wstring &pattern, int patternRuleIndex, Lexer *lexer); virtual tree::pattern::ParseTreePattern *compileParseTreePattern(const std::wstring &pattern, int patternRuleIndex, Lexer *lexer);
virtual ANTLRErrorStrategy *getErrorHandler(); virtual std::shared_ptr<ANTLRErrorStrategy> getErrorHandler();
virtual void setErrorHandler(std::shared_ptr<ANTLRErrorStrategy> handler);
virtual void setErrorHandler(ANTLRErrorStrategy *handler);
virtual TokenStream *getInputStream() override; virtual TokenStream *getInputStream() override;
void setInputStream(IntStream *input) override; void setInputStream(IntStream *input) override;
@ -395,12 +395,9 @@ namespace runtime {
virtual void setTrace(bool trace); virtual void setTrace(bool trace);
protected: protected:
/// <summary> /// The error handling strategy for the parser. The default is DefaultErrorStrategy.
/// The error handling strategy for the parser. The default value is a new /// See also getErrorHandler.
/// instance of <seealso cref="DefaultErrorStrategy"/>. std::shared_ptr<ANTLRErrorStrategy> _errHandler;
/// </summary>
/// <seealso cref= #getErrorHandler </seealso>
ANTLRErrorStrategy *_errHandler;
/// <summary> /// <summary>
/// The input stream. /// The input stream.
@ -444,14 +441,12 @@ namespace runtime {
/// <seealso cref= ATNDeserializationOptions#isGenerateRuleBypassTransitions() </seealso> /// <seealso cref= ATNDeserializationOptions#isGenerateRuleBypassTransitions() </seealso>
static std::map<std::wstring, atn::ATN> bypassAltsAtnCache; static std::map<std::wstring, atn::ATN> bypassAltsAtnCache;
/// <summary> /// When setTrace(true) is called, a reference to the
/// When <seealso cref="#setTrace"/>{@code (true)} is called, a reference to the /// TraceListener is stored here so it can be easily removed in a
/// <seealso cref="TraceListener"/> is stored here so it can be easily removed in a /// later call to setTrace(false). The listener itself is
/// later call to <seealso cref="#setTrace"/>{@code (false)}. The listener itself is
/// implemented as a parser listener so this field is not directly used by /// implemented as a parser listener so this field is not directly used by
/// other parser methods. /// other parser methods.
/// </summary> TraceListener _tracer;
TraceListener *_tracer;
void InitializeInstanceFields(); void InitializeInstanceFields();
}; };

View File

@ -37,7 +37,6 @@
#include "LoopEndState.h" #include "LoopEndState.h"
#include "FailedPredicateException.h" #include "FailedPredicateException.h"
#include "StarLoopEntryState.h" #include "StarLoopEntryState.h"
#include "PredictionContextCache.h"
#include "AtomTransition.h" #include "AtomTransition.h"
#include "RuleTransition.h" #include "RuleTransition.h"
#include "PredicateTransition.h" #include "PredicateTransition.h"
@ -52,9 +51,8 @@
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
ParserInterpreter::ParserInterpreter(const std::wstring &grammarFileName, const std::vector<std::wstring>& tokenNames, ParserInterpreter::ParserInterpreter(const std::wstring &grammarFileName, const std::vector<std::wstring>& tokenNames,
const std::vector<std::wstring>& ruleNames, const atn::ATN& atn, TokenStream *input) const std::vector<std::wstring>& ruleNames, const atn::ATN &atn, TokenStream *input)
: Parser(input), grammarFileName(grammarFileName), : Parser(input), _grammarFileName(grammarFileName), _tokenNames(tokenNames), _atn(atn), _ruleNames(ruleNames) {
_tokenNames(tokenNames), _atn(atn), _ruleNames(ruleNames), sharedContextCache(new atn::PredictionContextCache()), _parentContextStack(new std::deque<std::pair<ParserRuleContext *, int>*>()) {
for (int i = 0; i < _atn.getNumberOfDecisions(); i++) { for (int i = 0; i < _atn.getNumberOfDecisions(); i++) {
_decisionToDFA.push_back(new dfa::DFA(_atn.getDecisionState(i), i)); _decisionToDFA.push_back(new dfa::DFA(_atn.getDecisionState(i), i));
@ -82,7 +80,7 @@ ParserInterpreter::ParserInterpreter(const std::wstring &grammarFileName, const
} }
// get atn simulator that knows how to do predictions // get atn simulator that knows how to do predictions
_interpreter = new atn::ParserATNSimulator(this, atn, _decisionToDFA, sharedContextCache); _interpreter = new atn::ParserATNSimulator(this, atn, _decisionToDFA, _sharedContextCache);
} }
ParserInterpreter::~ParserInterpreter() { ParserInterpreter::~ParserInterpreter() {
@ -102,7 +100,7 @@ const std::vector<std::wstring>& ParserInterpreter::getRuleNames() const {
} }
std::wstring ParserInterpreter::getGrammarFileName() const { std::wstring ParserInterpreter::getGrammarFileName() const {
return grammarFileName; return _grammarFileName;
} }
ParserRuleContext *ParserInterpreter::parse(int startRuleIndex) { ParserRuleContext *ParserInterpreter::parse(int startRuleIndex) {
@ -136,7 +134,7 @@ ParserRuleContext *ParserInterpreter::parse(int startRuleIndex) {
} }
void ParserInterpreter::enterRecursionRule(ParserRuleContext *localctx, int state, int ruleIndex, int precedence) { void ParserInterpreter::enterRecursionRule(ParserRuleContext *localctx, int state, int ruleIndex, int precedence) {
_parentContextStack->push_back(new std::pair<ParserRuleContext*, int>(ctx, localctx->invokingState)); _parentContextStack.push({ ctx, localctx->invokingState });
Parser::enterRecursionRule(localctx, state, ruleIndex, precedence); Parser::enterRecursionRule(localctx, state, ruleIndex, precedence);
} }
@ -156,8 +154,10 @@ void ParserInterpreter::visitState(atn::ATNState *p) {
switch (transition->getSerializationType()) { switch (transition->getSerializationType()) {
case atn::Transition::EPSILON: case atn::Transition::EPSILON:
if (_pushRecursionContextStates.data[(size_t)p->stateNumber] == 1 && !(dynamic_cast<atn::LoopEndState*>(transition->target) != nullptr)) { if (_pushRecursionContextStates.data[(size_t)p->stateNumber] == 1 && !(dynamic_cast<atn::LoopEndState*>(transition->target) != nullptr)) {
InterpreterRuleContext *ruleContext = new InterpreterRuleContext(_parentContextStack->front()->first, _parentContextStack->front()->second, ctx->getRuleIndex()); InterpreterRuleContext *ruleContext = new InterpreterRuleContext(_parentContextStack.top().first,
pushNewRecursionContext(ruleContext, _atn.ruleToStartState[(size_t)p->ruleIndex]->stateNumber, (int)ruleContext->getRuleIndex()); _parentContextStack.top().second, ctx->getRuleIndex());
pushNewRecursionContext(ruleContext, _atn.ruleToStartState[(size_t)p->ruleIndex]->stateNumber,
(int)ruleContext->getRuleIndex());
} }
break; break;
@ -195,7 +195,7 @@ void ParserInterpreter::visitState(atn::ATNState *p) {
{ {
atn::PredicateTransition *predicateTransition = (atn::PredicateTransition*)(transition); atn::PredicateTransition *predicateTransition = (atn::PredicateTransition*)(transition);
if (!sempred(ctx, predicateTransition->ruleIndex, predicateTransition->predIndex)) { if (!sempred(ctx, predicateTransition->ruleIndex, predicateTransition->predIndex)) {
throw new FailedPredicateException(this); throw FailedPredicateException(this);
} }
} }
break; break;
@ -210,7 +210,7 @@ void ParserInterpreter::visitState(atn::ATNState *p) {
case atn::Transition::PRECEDENCE: case atn::Transition::PRECEDENCE:
{ {
if (!precpred(ctx, ((atn::PrecedencePredicateTransition*)(transition))->precedence)) { if (!precpred(ctx, ((atn::PrecedencePredicateTransition*)(transition))->precedence)) {
throw new FailedPredicateException(this, "precpred(_ctx, " + std::to_string(((atn::PrecedencePredicateTransition*)(transition))->precedence) + ")"); throw FailedPredicateException(this, "precpred(_ctx, " + std::to_string(((atn::PrecedencePredicateTransition*)(transition))->precedence) + ")");
} }
} }
break; break;
@ -225,10 +225,11 @@ void ParserInterpreter::visitState(atn::ATNState *p) {
void ParserInterpreter::visitRuleStopState(atn::ATNState *p) { void ParserInterpreter::visitRuleStopState(atn::ATNState *p) {
atn::RuleStartState *ruleStartState = _atn.ruleToStartState[(size_t)p->ruleIndex]; atn::RuleStartState *ruleStartState = _atn.ruleToStartState[(size_t)p->ruleIndex];
if (ruleStartState->isPrecedenceRule) { if (ruleStartState->isPrecedenceRule) {
std::pair<ParserRuleContext*, int> *parentContext = _parentContextStack->back(); // TODO: Dan - make sure this is equivalent std::pair<ParserRuleContext*, int> parentContext = _parentContextStack.top();
_parentContextStack->pop_back(); _parentContextStack.pop();
unrollRecursionContexts(parentContext->first);
setState(parentContext->second); unrollRecursionContexts(parentContext.first);
setState(parentContext.second);
} else { } else {
exitRule(); exitRule();
} }

View File

@ -34,6 +34,7 @@
#include "Parser.h" #include "Parser.h"
#include "ATN.h" #include "ATN.h"
#include "BitSet.h" #include "BitSet.h"
#include "PredictionContext.h"
namespace org { namespace org {
namespace antlr { namespace antlr {
@ -55,33 +56,14 @@ namespace runtime {
/// See TestParserInterpreter for examples. /// See TestParserInterpreter for examples.
/// </summary> /// </summary>
class ParserInterpreter : public Parser { class ParserInterpreter : public Parser {
protected:
//TODO check this
static const int DEFAULT_BITSET_SIZE = 1024; // atn->states.size() ideally
const std::wstring grammarFileName;
std::vector<std::wstring> _tokenNames;
const atn::ATN &_atn;
std::vector<std::wstring> _ruleNames;
antlrcpp::BitSet _pushRecursionContextStates;
std::vector<dfa::DFA *> _decisionToDFA; // not shared like it is for generated parsers
atn::PredictionContextCache *const sharedContextCache;
std::deque<std::pair<ParserRuleContext*, int>*> *const _parentContextStack;
public: public:
ParserInterpreter(const std::wstring &grammarFileName, const std::vector<std::wstring>& tokenNames, ParserInterpreter(const std::wstring &grammarFileName, const std::vector<std::wstring>& tokenNames,
const std::vector<std::wstring>& ruleNames, const atn::ATN &atn, TokenStream *input); const std::vector<std::wstring>& ruleNames, const atn::ATN &atn, TokenStream *input);
~ParserInterpreter(); ~ParserInterpreter();
virtual const atn::ATN& getATN() const override; virtual const atn::ATN& getATN() const override;
virtual const std::vector<std::wstring>& getTokenNames() const override; virtual const std::vector<std::wstring>& getTokenNames() const override;
virtual const std::vector<std::wstring>& getRuleNames() const override; virtual const std::vector<std::wstring>& getRuleNames() const override;
virtual std::wstring getGrammarFileName() const override; virtual std::wstring getGrammarFileName() const override;
/// Begin parsing at startRuleIndex /// Begin parsing at startRuleIndex
@ -90,6 +72,18 @@ namespace runtime {
virtual void enterRecursionRule(ParserRuleContext *localctx, int state, int ruleIndex, int precedence) override; virtual void enterRecursionRule(ParserRuleContext *localctx, int state, int ruleIndex, int precedence) override;
protected: protected:
const std::wstring _grammarFileName;
std::vector<std::wstring> _tokenNames;
const atn::ATN &_atn;
std::vector<std::wstring> _ruleNames;
antlrcpp::BitSet _pushRecursionContextStates;
std::vector<dfa::DFA *> _decisionToDFA; // not shared like it is for generated parsers
std::shared_ptr<atn::PredictionContextCache> _sharedContextCache;
std::stack<std::pair<ParserRuleContext*, int>> _parentContextStack;
virtual atn::ATNState *getATNState(); virtual atn::ATNState *getATNState();
virtual void visitState(atn::ATNState *p); virtual void visitState(atn::ATNState *p);
virtual void visitRuleStopState(atn::ATNState *p); virtual void visitRuleStopState(atn::ATNState *p);

View File

@ -61,24 +61,21 @@ void ParserRuleContext::exitRule(tree::ParseTreeListener *listener) {
} }
tree::TerminalNode *ParserRuleContext::addChild(tree::TerminalNode *t) { tree::TerminalNode *ParserRuleContext::addChild(tree::TerminalNode *t) {
if (_children.empty()) { if (children.empty()) {
_children = std::vector<ParseTree*>(); children = std::vector<ParseTree*>();
} }
_children.push_back(t); children.push_back(t);
return t; return t;
} }
RuleContext *ParserRuleContext::addChild(RuleContext *ruleInvocation) { RuleContext *ParserRuleContext::addChild(RuleContext *ruleInvocation) {
if (_children.empty()) { children.push_back(ruleInvocation);
_children = std::vector<ParseTree*>();
}
_children.push_back(ruleInvocation);
return ruleInvocation; return ruleInvocation;
} }
void ParserRuleContext::removeLastChild() { void ParserRuleContext::removeLastChild() {
if (_children.size() > 0) { if (!children.empty()) {
_children.pop_back(); children.pop_back();
} }
} }
@ -96,26 +93,23 @@ tree::ErrorNode *ParserRuleContext::addErrorNode(Token *badToken) {
return t; return t;
} }
/// <summary> /// Override to make type more specific
/// Override to make type more specific </summary>
ParserRuleContext *ParserRuleContext::getParent() ParserRuleContext *ParserRuleContext::getParent()
{ {
return static_cast<ParserRuleContext*>(RuleContext::getParent()); return static_cast<ParserRuleContext*>(RuleContext::getParent());
} }
tree::ParseTree *ParserRuleContext::getChild(std::size_t i) { tree::ParseTree *ParserRuleContext::getChild(std::size_t i) {
return _children.size() > 0 && i < _children.size() ? _children[i] : nullptr; return children[i];
} }
tree::TerminalNode *ParserRuleContext::getToken(int ttype, std::size_t i) { tree::TerminalNode *ParserRuleContext::getToken(int ttype, std::size_t i) {
if (_children.empty() || i >= _children.size()) { if (i >= children.size()) {
return nullptr; return nullptr;
} }
size_t j = 0; // what token with ttype have we found? size_t j = 0; // what token with ttype have we found?
for (auto &o : _children) { for (auto &o : children) {
if (dynamic_cast<tree::TerminalNode*>(o) != nullptr) { if (dynamic_cast<tree::TerminalNode*>(o) != nullptr) {
tree::TerminalNode *tnode = static_cast<tree::TerminalNode*>(o); tree::TerminalNode *tnode = static_cast<tree::TerminalNode*>(o);
Token *symbol = tnode->getSymbol(); Token *symbol = tnode->getSymbol();
@ -130,14 +124,9 @@ tree::TerminalNode *ParserRuleContext::getToken(int ttype, std::size_t i) {
return nullptr; return nullptr;
} }
// I think this should be changed to a pointer?
std::vector<tree::TerminalNode*> ParserRuleContext::getTokens(int ttype) { std::vector<tree::TerminalNode*> ParserRuleContext::getTokens(int ttype) {
if (_children.empty()) {
return std::vector<tree::TerminalNode*>();
}
std::vector<tree::TerminalNode*> tokens; std::vector<tree::TerminalNode*> tokens;
for (auto &o : _children) { for (auto &o : children) {
if (dynamic_cast<tree::TerminalNode*>(o) != nullptr) { if (dynamic_cast<tree::TerminalNode*>(o) != nullptr) {
tree::TerminalNode *tnode = static_cast<tree::TerminalNode*>(o); tree::TerminalNode *tnode = static_cast<tree::TerminalNode*>(o);
Token *symbol = tnode->getSymbol(); Token *symbol = tnode->getSymbol();
@ -150,17 +139,13 @@ std::vector<tree::TerminalNode*> ParserRuleContext::getTokens(int ttype) {
} }
} }
if (tokens.empty()) {
return std::vector<tree::TerminalNode*>();
}
return tokens; return tokens;
} }
std::size_t ParserRuleContext::getChildCount() { std::size_t ParserRuleContext::getChildCount() {
return _children.size() > 0 ? _children.size() : 0; return children.size();
} }
misc::Interval ParserRuleContext::getSourceInterval() { misc::Interval ParserRuleContext::getSourceInterval() {

View File

@ -71,7 +71,7 @@ namespace runtime {
/// how we parse this rule. /// how we parse this rule.
/// </summary> /// </summary>
public: public:
std::vector<ParseTree*> _children; std::vector<ParseTree*> children;
/// <summary> /// <summary>
/// For debugging/tracing purposes, we want to track all of the nodes in /// For debugging/tracing purposes, we want to track all of the nodes in
@ -139,12 +139,12 @@ namespace runtime {
template<typename T> template<typename T>
T* getChild(size_t i) { T* getChild(size_t i) {
if (_children.empty()) { if (children.empty()) {
return nullptr; return nullptr;
} }
size_t j = 0; // what element have we found with ctxType? size_t j = 0; // what element have we found with ctxType?
for (auto &child : _children) { for (auto &child : children) {
if (dynamic_cast<T *>(child) != nullptr) { if (dynamic_cast<T *>(child) != nullptr) {
if (j++ == i) { if (j++ == i) {
return dynamic_cast<T *>(child); return dynamic_cast<T *>(child);
@ -165,12 +165,12 @@ namespace runtime {
template<typename T> template<typename T>
std::vector<T*> getRuleContexts() { std::vector<T*> getRuleContexts() {
if (_children.empty()) { if (children.empty()) {
return std::vector<T *>(); return std::vector<T *>();
} }
std::vector<T *> contexts; std::vector<T *> contexts;
for (auto &child : _children) { for (auto &child : children) {
if (dynamic_cast<T *>(child)) { if (dynamic_cast<T *>(child)) {
if (contexts.empty()) { if (contexts.empty()) {
contexts = std::vector<T *>(); contexts = std::vector<T *>();

View File

@ -50,12 +50,12 @@ namespace runtime {
template<typename T1> //where T1 : ANTLRErrorListener template<typename T1> //where T1 : ANTLRErrorListener
ProxyErrorListener(std::vector<T1> *delegates) : delegates(delegates) { ProxyErrorListener(std::vector<T1> *delegates) : delegates(delegates) {
if (delegates == nullptr) { if (delegates == nullptr) {
throw new NullPointerException("delegates"); throw NullPointerException("delegates");
} }
} }
void syntaxError(IRecognizer *recognizer, void *offendingSymbol, size_t line, int charPositionInLine, void syntaxError(IRecognizer *recognizer, Token *offendingSymbol, size_t line, int charPositionInLine,
const std::wstring &msg, RecognitionException *e) { const std::wstring &msg, RecognitionException *e) override {
for (auto listener : *delegates) { for (auto listener : *delegates) {
listener->syntaxError(recognizer, offendingSymbol, line, charPositionInLine, msg, e); listener->syntaxError(recognizer, offendingSymbol, line, charPositionInLine, msg, e);
} }

View File

@ -85,16 +85,3 @@ std::shared_ptr<IRecognizer> RecognitionException::getRecognizer() {
void RecognitionException::InitializeInstanceFields() { void RecognitionException::InitializeInstanceFields() {
_offendingState = -1; _offendingState = -1;
} }
//------------------ ParseCancellationException ------------------------------------------------------------------------
ParseCancellationException::ParseCancellationException() : ParseCancellationException("", nullptr) {
}
ParseCancellationException::ParseCancellationException(RecognitionException *cause)
: ParseCancellationException("", cause) {
}
ParseCancellationException::ParseCancellationException(const std::string &msg, RecognitionException *cause)
: IllegalStateException(msg, cause) {
}

View File

@ -125,24 +125,6 @@ namespace runtime {
void InitializeInstanceFields(); void InitializeInstanceFields();
}; };
/**
* This exception is thrown to cancel a parsing operation. This exception does
* not extend RecognitionException, allowing it to bypass the standard
* error recovery mechanisms. BailErrorStrategy throws this exception in
* response to a parse error.
*/
class ParseCancellationException : public IllegalStateException {
public:
ParseCancellationException();
ParseCancellationException(RecognitionException *cause);
ParseCancellationException(const std::string &msg, RecognitionException *cause = nullptr);
};
class EmptyStackException : public RuntimeException {
public:
EmptyStackException() : RuntimeException() {};
};
} // namespace runtime } // namespace runtime
} // namespace v4 } // namespace v4
} // namespace antlr } // namespace antlr

View File

@ -56,7 +56,7 @@ std::map<std::wstring, int> Recognizer::getTokenTypeMap() {
result = iterator->second; result = iterator->second;
} else { } else {
result = antlrcpp::toMap(tokenNames); result = antlrcpp::toMap(tokenNames);
result[L"EOF"] = Token::_EOF; result[L"EOF"] = EOF;
_tokenTypeMapCache[tokenNames] = result; _tokenTypeMapCache[tokenNames] = result;
} }
@ -105,7 +105,7 @@ std::wstring Recognizer::getTokenErrorDisplay(Token *t) {
} }
std::wstring s = t->getText(); std::wstring s = t->getText();
if (s == L"") { if (s == L"") {
if (t->getType() == Token::_EOF) { if (t->getType() == EOF) {
s = L"<EOF>"; s = L"<EOF>";
} else { } else {
s = std::wstring(L"<") + std::to_wstring(t->getType()) + std::wstring(L">"); s = std::wstring(L"<") + std::to_wstring(t->getType()) + std::wstring(L">");
@ -124,7 +124,7 @@ void Recognizer::addErrorListener(ANTLRErrorListener *listener) {
throw L"listener cannot be null."; throw L"listener cannot be null.";
} }
_listeners.insert(_listeners.end(), listener); _listeners.push_back(listener);
} }
void Recognizer::removeErrorListener(ANTLRErrorListener *listener) { void Recognizer::removeErrorListener(ANTLRErrorListener *listener) {

View File

@ -40,11 +40,10 @@ namespace runtime {
class Recognizer : public IRecognizer { class Recognizer : public IRecognizer {
public: public:
static const int _EOF = -1; //static const int _EOF = -1; ml: we don't need it IntStream, nor in Token, nor here
Recognizer(); Recognizer();
private: private:
static std::map<std::vector<std::wstring>, std::map<std::wstring, int>> _tokenTypeMapCache; static std::map<std::vector<std::wstring>, std::map<std::wstring, int>> _tokenTypeMapCache;
static std::map<std::vector<std::wstring>, std::map<std::wstring, int>> _ruleIndexMapCache; static std::map<std::vector<std::wstring>, std::map<std::wstring, int>> _ruleIndexMapCache;

View File

@ -77,15 +77,12 @@ RuleContext *RuleContext::getParent() {
} }
void *RuleContext::getPayload() void *RuleContext::getPayload()
/// <summary>
/// Return the combined text of all child nodes. This method only considers /// Return the combined text of all child nodes. This method only considers
/// tokens which have been added to the parse tree. /// tokens which have been added to the parse tree.
/// <para> /// <para>
/// Since tokens on hidden channels (e.g. whitespace or comments) are not /// Since tokens on hidden channels (e.g. whitespace or comments) are not
/// added to the parse trees, they will not appear in the output of this /// added to the parse trees, they will not appear in the output of this
/// method. /// method.
/// </para>
/// </summary>
{ {
return this; return this;
} }
@ -95,12 +92,12 @@ std::wstring RuleContext::getText() {
return L""; return L"";
} }
antlrcpp::StringBuilder *builder = new antlrcpp::StringBuilder(); antlrcpp::StringBuilder builder;
for (size_t i = 0; i < getChildCount(); i++) { for (size_t i = 0; i < getChildCount(); i++) {
builder->append(getChild(i)->getText()); builder.append(getChild(i)->getText());
} }
return builder->toString(); return builder.toString();
} }
ssize_t RuleContext::getRuleIndex() const { ssize_t RuleContext::getRuleIndex() const {
@ -115,17 +112,6 @@ std::size_t RuleContext::getChildCount() {
return 0; return 0;
} }
#ifdef TODO
Future<JDialog*> *RuleContext::inspect(Parser *parser) {
return inspect(parser->getRuleNames());
}
Future<JDialog*> *RuleContext::inspect(const std::vector<std::wstring> &ruleNames) {
TreeViewer *viewer = new TreeViewer(ruleNames, this);
return viewer->open();
}
#endif
void RuleContext::save(Parser *parser, const std::wstring &fileName) { void RuleContext::save(Parser *parser, const std::wstring &fileName) {
std::vector<std::wstring> ruleNames; std::vector<std::wstring> ruleNames;
if (parser != nullptr) { if (parser != nullptr) {

View File

@ -29,6 +29,8 @@
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/ */
#include "Strings.h"
#include "Token.h" #include "Token.h"
using namespace org::antlr::v4::runtime; using namespace org::antlr::v4::runtime;
@ -36,6 +38,25 @@ using namespace org::antlr::v4::runtime;
const size_t Token::INVALID_TYPE; const size_t Token::INVALID_TYPE;
const ssize_t Token::EPSILON; const ssize_t Token::EPSILON;
const size_t Token::MIN_USER_TOKEN_TYPE; const size_t Token::MIN_USER_TOKEN_TYPE;
const size_t Token::_EOF;
const size_t Token::DEFAULT_CHANNEL; const size_t Token::DEFAULT_CHANNEL;
const size_t Token::HIDDEN_CHANNEL; const size_t Token::HIDDEN_CHANNEL;
std::wstring Token::toString() {
std::wstringstream ss;
std::wstring txt = getText();
if (!txt.empty()) {
antlrcpp::replaceAll(txt, L"\n", L"\\n");
antlrcpp::replaceAll(txt, L"\r", L"\\r");
antlrcpp::replaceAll(txt, L"\t", L"\\t");
} else {
txt = L"<no text>";
}
ss << L"{Token: " << txt << L", channel: " << getChannel() << L", type: " << getType() << L", start: " << getStartIndex() <<
L", stop: " << getStopIndex() << L", index: " << getTokenIndex() << L", line: " << getLine() << L", offset: " <<
getCharPositionInLine() << L"}";
return ss.str();
}

View File

@ -55,7 +55,7 @@ namespace runtime {
static const size_t MIN_USER_TOKEN_TYPE = 1; static const size_t MIN_USER_TOKEN_TYPE = 1;
static const size_t _EOF = IntStream::_EOF; //static const size_t _EOF = IntStream::_EOF; no need to define another EOF.
// This isn't necessary // This isn't necessary
virtual ~Token() {}; virtual ~Token() {};
@ -132,6 +132,8 @@ namespace runtime {
/// Gets the <seealso cref="CharStream"/> from which this token was derived. /// Gets the <seealso cref="CharStream"/> from which this token was derived.
/// </summary> /// </summary>
virtual CharStream *getInputStream() = 0; virtual CharStream *getInputStream() = 0;
virtual std::wstring toString();
}; };
} // namespace runtime } // namespace runtime

View File

@ -76,7 +76,7 @@ TokenStreamRewriter::InsertBeforeOp::InsertBeforeOp(TokenStreamRewriter *outerIn
size_t TokenStreamRewriter::InsertBeforeOp::execute(std::wstring *buf) { size_t TokenStreamRewriter::InsertBeforeOp::execute(std::wstring *buf) {
buf->append(text); buf->append(text);
if (outerInstance->tokens->get(index)->getType() != Token::_EOF) { if (outerInstance->tokens->get(index)->getType() != EOF) {
buf->append(outerInstance->tokens->get(index)->getText()); buf->append(outerInstance->tokens->get(index)->getText());
} }
return index + 1; return index + 1;
@ -290,7 +290,7 @@ std::wstring TokenStreamRewriter::getText(const std::wstring &programName, const
Token *t = tokens->get(i); Token *t = tokens->get(i);
if (op == nullptr) { if (op == nullptr) {
// no operation at that index, just dump token // no operation at that index, just dump token
if (t->getType() != Token::_EOF) { if (t->getType() != EOF) {
buf.append(t->getText()); buf.append(t->getText());
} }
i++; // move to next token i++; // move to next token
@ -421,7 +421,7 @@ std::unordered_map<int, TokenStreamRewriter::RewriteOperation*> *TokenStreamRewr
} }
if (m->at((int)op->index) != nullptr) { if (m->at((int)op->index) != nullptr) {
// TODO: use a specific exception rather than a generic type here? // TODO: use a specific exception rather than a generic type here?
throw new RuntimeException("should only be one op per index"); throw RuntimeException("should only be one op per index");
} }
m->emplace(op->index, op); m->emplace(op->index, op);
} }

View File

@ -54,7 +54,7 @@ UnbufferedCharStream::UnbufferedCharStream(std::ifstream *input, int bufferSize)
} }
void UnbufferedCharStream::consume() { void UnbufferedCharStream::consume() {
if (LA(1) == IntStream::_EOF) { if (LA(1) == EOF) {
throw IllegalStateException("cannot consume EOF"); throw IllegalStateException("cannot consume EOF");
} }
@ -82,7 +82,7 @@ void UnbufferedCharStream::sync(size_t want) {
size_t UnbufferedCharStream::fill(size_t n) { size_t UnbufferedCharStream::fill(size_t n) {
for (size_t i = 0; i < n; i++) { for (size_t i = 0; i < n; i++) {
if (this->n > 0 && data[this->n - 1] == static_cast<wchar_t>(IntStream::_EOF)) { if (this->n > 0 && data[this->n - 1] == static_cast<wchar_t>(EOF)) {
return i; return i;
} }
@ -108,21 +108,23 @@ void UnbufferedCharStream::add(size_t c) {
data[n++] = static_cast<wchar_t>(c); data[n++] = static_cast<wchar_t>(c);
} }
size_t UnbufferedCharStream::LA(ssize_t i) { ssize_t UnbufferedCharStream::LA(ssize_t i) {
if (i == -1) { // special case if (i == -1) { // special case
return (size_t)lastChar; return lastChar;
} }
sync((size_t)i); sync((size_t)i);
ssize_t index = (ssize_t)p + i - 1; ssize_t index = (ssize_t)p + i - 1;
if (index < 0) { if (index < 0) {
throw new IndexOutOfBoundsException(); throw IndexOutOfBoundsException();
} }
if ((size_t)index >= n) { if ((size_t)index >= n) {
return IntStream::_EOF; return EOF;
} }
size_t c = (size_t)data[(size_t)index];
if (c == IntStream::_EOF) { ssize_t c = data[(size_t)index];
return IntStream::_EOF; if (c == EOF) {
return EOF;
} }
return c; return c;
} }

View File

@ -144,7 +144,7 @@ namespace runtime {
virtual void add(size_t c); virtual void add(size_t c);
public: public:
virtual size_t LA(ssize_t i) override; virtual ssize_t LA(ssize_t i) override;
/// <summary> /// <summary>
/// Return a marker that we can release later. /// Return a marker that we can release later.

View File

@ -58,7 +58,7 @@ Token* UnbufferedTokenStream::get(int i)
{ // get absolute index { // get absolute index
int bufferStartIndex = getBufferStartIndex(); int bufferStartIndex = getBufferStartIndex();
if (i < bufferStartIndex || i >= bufferStartIndex + n) { if (i < bufferStartIndex || i >= bufferStartIndex + n) {
throw new IndexOutOfBoundsException(std::wstring(L"get(") + std::to_wstring(i) + std::wstring(L") outside buffer: ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStartIndex + n)); throw IndexOutOfBoundsException(std::wstring(L"get(") + std::to_wstring(i) + std::wstring(L") outside buffer: ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStartIndex + n));
} }
return tokens[i - bufferStartIndex]; return tokens[i - bufferStartIndex];
} }
@ -72,11 +72,11 @@ Token* UnbufferedTokenStream::LT(ssize_t i)
sync(i); sync(i);
int index = p + i - 1; int index = p + i - 1;
if (index < 0) { if (index < 0) {
throw new IndexOutOfBoundsException(std::wstring(L"LT(") + std::to_wstring(i) + std::wstring(L") gives negative index")); throw IndexOutOfBoundsException(std::wstring(L"LT(") + std::to_wstring(i) + std::wstring(L") gives negative index"));
} }
if (index >= tokens.size()) { if (index >= tokens.size()) {
assert(n > 0 && tokens[n - 1]->getType() == Token::_EOF); assert(n > 0 && tokens[n - 1]->getType() == EOF);
return tokens[n - 1]; return tokens[n - 1];
} }
@ -110,8 +110,8 @@ std::wstring UnbufferedTokenStream::getText(Token* start, Token* stop)
void UnbufferedTokenStream::consume() void UnbufferedTokenStream::consume()
{ {
if (LA(1) == Token::_EOF) { if (LA(1) == EOF) {
throw new IllegalStateException(L"cannot consume EOF"); throw IllegalStateException(L"cannot consume EOF");
} }
// buf always has at least tokens[p==0] in this method due to ctor // buf always has at least tokens[p==0] in this method due to ctor
@ -150,7 +150,7 @@ void UnbufferedTokenStream::sync(int want)
int UnbufferedTokenStream::fill(int n) int UnbufferedTokenStream::fill(int n)
{ {
for (int i = 0; i < n; i++) { for (int i = 0; i < n; i++) {
if (this->n > 0 && tokens[this->n - 1]->getType() == Token::_EOF) { if (this->n > 0 && tokens[this->n - 1]->getType() == EOF) {
return i; return i;
} }
@ -231,10 +231,10 @@ void UnbufferedTokenStream::seek(size_t index)
int bufferStartIndex = getBufferStartIndex(); int bufferStartIndex = getBufferStartIndex();
int i = index - bufferStartIndex; int i = index - bufferStartIndex;
if (i < 0) { if (i < 0) {
throw new IllegalArgumentException(std::wstring(L"cannot seek to negative index ") + std::to_wstring(index)); throw IllegalArgumentException(std::wstring(L"cannot seek to negative index ") + std::to_wstring(index));
} }
else if (i >= n) { else if (i >= n) {
throw new UnsupportedOperationException(std::wstring(L"seek to index outside buffer: ") + std::to_wstring(index) + std::wstring(L" not in ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStartIndex + n)); throw UnsupportedOperationException(std::wstring(L"seek to index outside buffer: ") + std::to_wstring(index) + std::wstring(L" not in ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStartIndex + n));
} }
p = i; p = i;
@ -249,7 +249,7 @@ void UnbufferedTokenStream::seek(size_t index)
size_t UnbufferedTokenStream::size() size_t UnbufferedTokenStream::size()
{ {
throw new UnsupportedOperationException(L"Unbuffered stream cannot know its size"); throw UnsupportedOperationException(L"Unbuffered stream cannot know its size");
} }
std::string UnbufferedTokenStream::getSourceName() std::string UnbufferedTokenStream::getSourceName()
@ -265,7 +265,7 @@ std::wstring UnbufferedTokenStream::getText(const misc::Interval &interval)
int start = interval->a; int start = interval->a;
int stop = interval->b; int stop = interval->b;
if (start < bufferStartIndex || stop > bufferStopIndex) { if (start < bufferStartIndex || stop > bufferStopIndex) {
throw new UnsupportedOperationException(std::wstring(L"interval ") + interval->toString() + std::wstring(L" not in token buffer window: ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStopIndex)); throw UnsupportedOperationException(std::wstring(L"interval ") + interval->toString() + std::wstring(L" not in token buffer window: ") + std::to_wstring(bufferStartIndex) + std::wstring(L"..") + std::to_wstring(bufferStopIndex));
} }
int a = start - bufferStartIndex; int a = start - bufferStartIndex;

View File

@ -96,7 +96,7 @@ namespace runtime {
virtual Token *LT(ssize_t i) override; virtual Token *LT(ssize_t i) override;
virtual size_t LA(ssize_t i) override; virtual ssize_t LA(ssize_t i) override;
virtual TokenSource *getTokenSource() const override; virtual TokenSource *getTokenSource() const override;

View File

@ -35,7 +35,7 @@
#include <algorithm> #include <algorithm>
#include <assert.h> #include <assert.h>
#include <codecvt> #include <codecvt>
#include <deque> #include <chrono>
#include <fstream> #include <fstream>
#include <iostream> #include <iostream>
#include <limits.h> #include <limits.h>
@ -47,6 +47,7 @@
#include <stdint.h> #include <stdint.h>
#include <stdlib.h> #include <stdlib.h>
#include <sstream> #include <sstream>
#include <stack>
#include <string> #include <string>
#include <typeinfo> #include <typeinfo>
#include <unordered_map> #include <unordered_map>

View File

@ -97,7 +97,7 @@ int ATN::getNumberOfDecisions() const {
misc::IntervalSet ATN::getExpectedTokens(int stateNumber, RuleContext *context) const { misc::IntervalSet ATN::getExpectedTokens(int stateNumber, RuleContext *context) const {
if (stateNumber < 0 || stateNumber >= (int)states.size()) { if (stateNumber < 0 || stateNumber >= (int)states.size()) {
throw new IllegalArgumentException("Invalid state number."); throw IllegalArgumentException("Invalid state number.");
} }
RuleContext *ctx = context; RuleContext *ctx = context;
@ -120,7 +120,7 @@ misc::IntervalSet ATN::getExpectedTokens(int stateNumber, RuleContext *context)
} }
if (following.contains(Token::EPSILON)) { if (following.contains(Token::EPSILON)) {
expected.add(Token::_EOF); expected.add(EOF);
} }
return expected; return expected;

View File

@ -37,48 +37,43 @@
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
ATNConfig::ATNConfig(ATNConfig *old) : state(old->state), alt(old->alt), semanticContext(old->semanticContext) { ATNConfig::ATNConfig(ATNState *state, int alt, PredictionContextRef context)
InitializeInstanceFields(); : ATNConfig(state, alt, context, SemanticContext::NONE) {
this->context = old->context;
this->reachesIntoOuterContext = old->reachesIntoOuterContext;
} }
ATNConfig::ATNConfig(ATNState *state, int alt, PredictionContext *context) : state(state), alt(alt), context(context), semanticContext(nullptr) { ATNConfig::ATNConfig(ATNState *state, int alt, PredictionContextRef context, SemanticContextRef semanticContext)
: state(state), alt(alt), context(context), semanticContext(semanticContext) {
reachesIntoOuterContext = 0;
} }
ATNConfig::ATNConfig(ATNState *state, int alt, PredictionContext *context, SemanticContext *semanticContext) : state(state), alt(alt), semanticContext(semanticContext) { ATNConfig::ATNConfig(ATNConfig *c) : ATNConfig(c, c->state, c->context, c->semanticContext) {
InitializeInstanceFields();
this->context = context;
} }
ATNConfig::ATNConfig(ATNConfig *c, ATNState *state) : state(state), alt(0), context(nullptr), semanticContext(nullptr) ATNConfig::ATNConfig(ATNConfig *c, ATNState *state) : ATNConfig(c, state, c->context, c->semanticContext) {
{
} }
ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, SemanticContext *semanticContext) : state(state), alt(0), context(nullptr), semanticContext(semanticContext) ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, SemanticContextRef semanticContext)
{ : ATNConfig(c, state, c->context, semanticContext) {
} }
ATNConfig::ATNConfig(ATNConfig *c, SemanticContext *semanticContext) : state(nullptr), alt(0), context(nullptr), semanticContext(semanticContext) ATNConfig::ATNConfig(ATNConfig *c, SemanticContextRef semanticContext)
{ : ATNConfig(c, c->state, c->context, semanticContext) {
} }
ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, PredictionContext *context) : state(state), alt(0), context(context), semanticContext(nullptr) ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, PredictionContextRef context)
{ : ATNConfig(c, state, context, c->semanticContext) {
} }
ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, PredictionContext *context, SemanticContext *semanticContext) : state(state), alt(c->alt), semanticContext(semanticContext) { ATNConfig::ATNConfig(ATNConfig *c, ATNState *state, PredictionContextRef context, SemanticContextRef semanticContext)
InitializeInstanceFields(); : state(state), alt(c->alt), context(context), semanticContext(semanticContext), reachesIntoOuterContext(c->reachesIntoOuterContext) {
this->context = context;
this->reachesIntoOuterContext = c->reachesIntoOuterContext;
} }
size_t ATNConfig::hashCode() const { size_t ATNConfig::hashCode() const {
size_t hashCode = misc::MurmurHash::initialize(7); size_t hashCode = misc::MurmurHash::initialize(7);
hashCode = misc::MurmurHash::update(hashCode, (size_t)state->stateNumber); hashCode = misc::MurmurHash::update(hashCode, (size_t)state->stateNumber);
hashCode = misc::MurmurHash::update(hashCode, (size_t)alt); hashCode = misc::MurmurHash::update(hashCode, (size_t)alt);
hashCode = misc::MurmurHash::update(hashCode, (size_t)context); hashCode = misc::MurmurHash::update(hashCode, (size_t)context.get());
hashCode = misc::MurmurHash::update(hashCode, (size_t)semanticContext); hashCode = misc::MurmurHash::update(hashCode, (size_t)semanticContext.get());
hashCode = misc::MurmurHash::finish(hashCode, 4); hashCode = misc::MurmurHash::finish(hashCode, 4);
return hashCode; return hashCode;
} }
@ -93,8 +88,3 @@ bool ATNConfig::operator == (const ATNConfig& other) const
std::wstring ATNConfig::toString() { std::wstring ATNConfig::toString() {
return toString(true); return toString(true);
} }
void ATNConfig::InitializeInstanceFields() {
reachesIntoOuterContext = 0;
}

View File

@ -58,14 +58,13 @@ namespace atn {
/// What alt (or lexer rule) is predicted by this configuration </summary> /// What alt (or lexer rule) is predicted by this configuration </summary>
const int alt; const int alt;
/// <summary>
/// The stack of invoking states leading to the rule/states associated /// The stack of invoking states leading to the rule/states associated
/// with this config. We track only those contexts pushed during /// with this config. We track only those contexts pushed during
/// execution of the ATN simulator. /// execution of the ATN simulator.
/// </summary> ///
PredictionContext *context; /// Can be shared between multiple ANTConfig instances.
PredictionContextRef context;
/// <summary>
/// We cannot execute predicates dependent upon local context unless /// We cannot execute predicates dependent upon local context unless
/// we know for sure we are in the correct context. Because there is /// we know for sure we are in the correct context. Because there is
/// no way to do this efficiently, we simply cannot evaluate /// no way to do this efficiently, we simply cannot evaluate
@ -74,20 +73,21 @@ namespace atn {
/// ///
/// closure() tracks the depth of how far we dip into the /// closure() tracks the depth of how far we dip into the
/// outer context: depth > 0. Note that it may not be totally /// outer context: depth > 0. Note that it may not be totally
/// accurate depth since I don't ever decrement. TODO: make it a boolean then /// accurate depth since I don't ever decrement. TO_DO: make it a boolean then
/// </summary>
int reachesIntoOuterContext; int reachesIntoOuterContext;
SemanticContext *const semanticContext; /// Can be shared between multiple ATNConfig instances.
SemanticContextRef semanticContext;
ATNConfig(ATNConfig *old); // dup ATNConfig(ATNState *state, int alt, PredictionContextRef context);
ATNConfig(ATNState *state, int alt, PredictionContext *context); //this(state, alt, context, SemanticContext.NONE); ATNConfig(ATNState *state, int alt, PredictionContextRef context, SemanticContextRef semanticContext);
ATNConfig(ATNState *state, int alt, PredictionContext *context, SemanticContext *semanticContext);
ATNConfig(ATNConfig *c, ATNState *state); //this(c, state, c.context, c.semanticContext); ATNConfig(ATNConfig *c); // dup
ATNConfig(ATNConfig *c, ATNState *state, SemanticContext *semanticContext); //this(c, state, c.context, semanticContext); ATNConfig(ATNConfig *c, ATNState *state);
ATNConfig(ATNConfig *c, SemanticContext *semanticContext); //this(c, c.state, c.context, semanticContext); ATNConfig(ATNConfig *c, ATNState *state, SemanticContextRef semanticContext);
ATNConfig(ATNConfig *c, ATNState *state, PredictionContext *context); //this(c, state, context, c.semanticContext); ATNConfig(ATNConfig *c, SemanticContextRef semanticContext);
ATNConfig(ATNConfig *c, ATNState *state, PredictionContext *context, SemanticContext *semanticContext); ATNConfig(ATNConfig *c, ATNState *state, PredictionContextRef context);
ATNConfig(ATNConfig *c, ATNState *state, PredictionContextRef context, SemanticContextRef semanticContext);
virtual size_t hashCode() const; virtual size_t hashCode() const;
@ -128,7 +128,7 @@ namespace atn {
} }
if (semanticContext != nullptr && semanticContext != SemanticContext::NONE) { if (semanticContext != nullptr && semanticContext != SemanticContext::NONE) {
buf.append(L","); buf.append(L",");
buf.append(semanticContext); buf.append(semanticContext.get());
} }
if (reachesIntoOuterContext > 0) { if (reachesIntoOuterContext > 0) {
buf.append(L",up=").append(reachesIntoOuterContext); buf.append(L",up=").append(reachesIntoOuterContext);
@ -138,8 +138,6 @@ namespace atn {
return buf.toString(); return buf.toString();
} }
private:
void InitializeInstanceFields();
}; };
} // namespace atn } // namespace atn

View File

@ -57,12 +57,12 @@ bool SimpleATNConfigComparer::operator () (const ATNConfig &lhs, const ATNConfig
//------------------ ATNConfigSet -------------------------------------------------------------------------------------- //------------------ ATNConfigSet --------------------------------------------------------------------------------------
ATNConfigSet::ATNConfigSet(bool fullCtx, ConfigLookup *lookup) : fullCtx(fullCtx) { ATNConfigSet::ATNConfigSet(bool fullCtx, std::shared_ptr<ConfigLookup> lookup) : fullCtx(fullCtx) {
configLookup = (lookup == nullptr) ? new ConfigLookupImpl<SimpleATNConfigHasher, SimpleATNConfigComparer>() : lookup; configLookup = !lookup ? std::shared_ptr<ConfigLookup>(new ConfigLookupImpl<SimpleATNConfigHasher, SimpleATNConfigComparer>()) : lookup;
InitializeInstanceFields(); InitializeInstanceFields();
} }
ATNConfigSet::ATNConfigSet(ATNConfigSet *old) : ATNConfigSet(old->fullCtx) { ATNConfigSet::ATNConfigSet(ATNConfigSet *old) : ATNConfigSet(old->fullCtx, std::shared_ptr<ConfigLookup>()) {
addAll(old); addAll(old);
uniqueAlt = old->uniqueAlt; uniqueAlt = old->uniqueAlt;
conflictingAlts = old->conflictingAlts; conflictingAlts = old->conflictingAlts;
@ -71,16 +71,15 @@ ATNConfigSet::ATNConfigSet(ATNConfigSet *old) : ATNConfigSet(old->fullCtx) {
} }
ATNConfigSet::~ATNConfigSet() { ATNConfigSet::~ATNConfigSet() {
delete configLookup;
} }
bool ATNConfigSet::add(ATNConfig *config) { bool ATNConfigSet::add(ATNConfig *config) {
return add(config, nullptr); return add(config, nullptr);
} }
bool ATNConfigSet::add(ATNConfig *config, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache) { bool ATNConfigSet::add(ATNConfig *config, PredictionContextMergeCache *mergeCache) {
if (_readonly) { if (_readonly) {
throw new IllegalStateException("This set is readonly"); throw IllegalStateException("This set is readonly");
} }
if (config->semanticContext != SemanticContext::NONE) { if (config->semanticContext != SemanticContext::NONE) {
hasSemanticContext = true; hasSemanticContext = true;
@ -98,7 +97,7 @@ bool ATNConfigSet::add(ATNConfig *config, misc::DoubleKeyMap<PredictionContext*,
} }
// a previous (s,i,pi,_), merge with it and save result // a previous (s,i,pi,_), merge with it and save result
bool rootIsWildcard = !fullCtx; bool rootIsWildcard = !fullCtx;
PredictionContext *merged = PredictionContext::merge(existing->context, config->context, rootIsWildcard, mergeCache); PredictionContextRef merged = PredictionContext::merge(existing->context, config->context, rootIsWildcard, mergeCache);
// no need to check for existing.context, config.context in cache // no need to check for existing.context, config.context in cache
// since only way to create new graphs is "call rule" and here. We // since only way to create new graphs is "call rule" and here. We
// cache at both places. // cache at both places.
@ -126,8 +125,8 @@ std::vector<ATNState*>* ATNConfigSet::getStates() {
return states; return states;
} }
std::vector<SemanticContext*> ATNConfigSet::getPredicates() { std::vector<SemanticContextRef> ATNConfigSet::getPredicates() {
std::vector<SemanticContext*> preds = std::vector<SemanticContext*>(); std::vector<SemanticContextRef> preds;
for (auto c : configs) { for (auto c : configs) {
if (c->semanticContext != SemanticContext::NONE) { if (c->semanticContext != SemanticContext::NONE) {
preds.push_back(c->semanticContext); preds.push_back(c->semanticContext);
@ -211,7 +210,7 @@ bool ATNConfigSet::contains(ATNConfig *o) {
void ATNConfigSet::clear() { void ATNConfigSet::clear() {
if (_readonly) { if (_readonly) {
throw new IllegalStateException("This set is readonly"); throw IllegalStateException("This set is readonly");
} }
configs.clear(); configs.clear();
_cachedHashCode = 0; _cachedHashCode = 0;
@ -224,8 +223,7 @@ bool ATNConfigSet::isReadonly() {
void ATNConfigSet::setReadonly(bool readonly) { void ATNConfigSet::setReadonly(bool readonly) {
_readonly = readonly; _readonly = readonly;
delete configLookup; configLookup.reset();
configLookup = nullptr; // can't mod, no need for lookup cache
} }
std::wstring ATNConfigSet::toString() { std::wstring ATNConfigSet::toString() {

View File

@ -59,14 +59,14 @@ namespace atn {
/// All configs but hashed by (s, i, _, pi) not including context. Wiped out /// All configs but hashed by (s, i, _, pi) not including context. Wiped out
/// when we go readonly as this set becomes a DFA state. /// when we go readonly as this set becomes a DFA state.
/// </summary> /// </summary>
ConfigLookup *configLookup; std::shared_ptr<ConfigLookup> configLookup;
/// <summary> /// <summary>
/// Track the elements as they are added to the set; supports get(i) </summary> /// Track the elements as they are added to the set; supports get(i) </summary>
std::vector<ATNConfig *> configs; std::vector<ATNConfig *> configs;
// TODO: these fields make me pretty uncomfortable but nice to pack up info together, saves recomputation // TO_DO: these fields make me pretty uncomfortable but nice to pack up info together, saves recomputation
// TODO: can we track conflicts as they are added to save scanning configs later? // TO_DO: can we track conflicts as they are added to save scanning configs later?
int uniqueAlt; int uniqueAlt;
antlrcpp::BitSet *conflictingAlts; antlrcpp::BitSet *conflictingAlts;
@ -83,7 +83,7 @@ namespace atn {
/// </summary> /// </summary>
const bool fullCtx; const bool fullCtx;
ATNConfigSet(bool fullCtx = true, ConfigLookup *lookup = nullptr); ATNConfigSet(bool fullCtx, std::shared_ptr<ConfigLookup> lookup);
ATNConfigSet(ATNConfigSet *old); ATNConfigSet(ATNConfigSet *old);
virtual ~ATNConfigSet(); virtual ~ATNConfigSet();
@ -100,7 +100,7 @@ namespace atn {
/// This method updates <seealso cref="#dipsIntoOuterContext"/> and /// This method updates <seealso cref="#dipsIntoOuterContext"/> and
/// <seealso cref="#hasSemanticContext"/> when necessary. /// <seealso cref="#hasSemanticContext"/> when necessary.
/// </summary> /// </summary>
virtual bool add(ATNConfig *config, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache); virtual bool add(ATNConfig *config, PredictionContextMergeCache *mergeCache);
/// <summary> /// <summary>
/// Return a List holding list of configs </summary> /// Return a List holding list of configs </summary>
@ -108,7 +108,7 @@ namespace atn {
virtual std::vector<ATNState*> *getStates(); virtual std::vector<ATNState*> *getStates();
virtual std::vector<SemanticContext*> getPredicates(); virtual std::vector<SemanticContextRef> getPredicates();
virtual ATNConfig *get(size_t i) const; virtual ATNConfig *get(size_t i) const;

View File

@ -203,7 +203,7 @@ ATN ATNDeserializer::deserialize(const std::wstring& input) {
if (atn.grammarType == ATNType::LEXER) { if (atn.grammarType == ATNType::LEXER) {
int tokenType = data[p++]; int tokenType = data[p++];
if (tokenType == 0xFFFF) { if (tokenType == 0xFFFF) {
tokenType = Token::_EOF; tokenType = EOF;
} }
atn.ruleToTokenType[i] = tokenType; atn.ruleToTokenType[i] = tokenType;
@ -292,12 +292,12 @@ ATN ATNDeserializer::deserialize(const std::wstring& input) {
if (dynamic_cast<BlockStartState*>(state) != nullptr) { if (dynamic_cast<BlockStartState*>(state) != nullptr) {
// we need to know the end state to set its start state // we need to know the end state to set its start state
if ((static_cast<BlockStartState*>(state))->endState == nullptr) { if ((static_cast<BlockStartState*>(state))->endState == nullptr) {
throw new IllegalStateException(); throw IllegalStateException();
} }
// block end states can only be associated to a single block start state // block end states can only be associated to a single block start state
if ((static_cast<BlockStartState*>(state))->endState->startState != nullptr) { if ((static_cast<BlockStartState*>(state))->endState->startState != nullptr) {
throw new IllegalStateException(); throw IllegalStateException();
} }
@ -456,7 +456,7 @@ void ATNDeserializer::verifyATN(const ATN &atn) {
checkCondition(dynamic_cast<StarBlockStartState*>(starLoopEntryState->transition(1)->target) != nullptr); checkCondition(dynamic_cast<StarBlockStartState*>(starLoopEntryState->transition(1)->target) != nullptr);
checkCondition(starLoopEntryState->nonGreedy); checkCondition(starLoopEntryState->nonGreedy);
} else { } else {
throw new IllegalStateException(); throw IllegalStateException();
} }
} }
@ -514,7 +514,7 @@ Transition *ATNDeserializer::edgeFactory(const ATN &atn, int type, int src, int
return new EpsilonTransition(target); return new EpsilonTransition(target);
case Transition::RANGE : case Transition::RANGE :
if (arg3 != 0) { if (arg3 != 0) {
return new RangeTransition(target, Token::_EOF, arg2); return new RangeTransition(target, EOF, arg2);
} else { } else {
return new RangeTransition(target, arg1, arg2); return new RangeTransition(target, arg1, arg2);
} }
@ -526,7 +526,7 @@ Transition *ATNDeserializer::edgeFactory(const ATN &atn, int type, int src, int
return new PrecedencePredicateTransition(target, arg1); return new PrecedencePredicateTransition(target, arg1);
case Transition::ATOM : case Transition::ATOM :
if (arg3 != 0) { if (arg3 != 0) {
return new AtomTransition(target, Token::_EOF); return new AtomTransition(target, EOF);
} else { } else {
return new AtomTransition(target, arg1); return new AtomTransition(target, arg1);
} }

View File

@ -156,7 +156,7 @@ std::vector<size_t>* ATNSerializer::serialize() {
ATNState *ruleStartState = atn->ruleToStartState[r]; ATNState *ruleStartState = atn->ruleToStartState[r];
data->push_back((size_t)ruleStartState->stateNumber); data->push_back((size_t)ruleStartState->stateNumber);
if (atn->grammarType == ATNType::LEXER) { if (atn->grammarType == ATNType::LEXER) {
if (atn->ruleToTokenType[r] == Token::_EOF) { if (atn->ruleToTokenType[r] == EOF) {
data->push_back(WCHAR_MAX); data->push_back(WCHAR_MAX);
} }
else { else {
@ -183,8 +183,8 @@ std::vector<size_t>* ATNSerializer::serialize() {
size_t nsets = sets.size(); size_t nsets = sets.size();
data->push_back(nsets); data->push_back(nsets);
for (auto set : sets) { for (auto set : sets) {
bool containsEof = set.contains(Token::_EOF); bool containsEof = set.contains(EOF);
if (containsEof && set.getIntervals().at(0).b == Token::_EOF) { if (containsEof && set.getIntervals().at(0).b == EOF) {
data->push_back(set.getIntervals().size() - 1); data->push_back(set.getIntervals().size() - 1);
} }
else { else {
@ -193,8 +193,8 @@ std::vector<size_t>* ATNSerializer::serialize() {
data->push_back(containsEof ? 1 : 0); data->push_back(containsEof ? 1 : 0);
for (auto &interval : set.getIntervals()) { for (auto &interval : set.getIntervals()) {
if (interval.a == Token::_EOF) { if (interval.a == EOF) {
if (interval.b == Token::_EOF) { if (interval.b == EOF) {
continue; continue;
} else { } else {
data->push_back(0); data->push_back(0);
@ -257,7 +257,7 @@ std::vector<size_t>* ATNSerializer::serialize() {
case Transition::RANGE: case Transition::RANGE:
arg1 = (static_cast<RangeTransition *>(t))->from; arg1 = (static_cast<RangeTransition *>(t))->from;
arg2 = (static_cast<RangeTransition *>(t))->to; arg2 = (static_cast<RangeTransition *>(t))->to;
if (arg1 == Token::_EOF) { if (arg1 == EOF) {
arg1 = 0; arg1 = 0;
arg3 = 1; arg3 = 1;
} }
@ -265,7 +265,7 @@ std::vector<size_t>* ATNSerializer::serialize() {
break; break;
case Transition::ATOM: case Transition::ATOM:
arg1 = (static_cast<AtomTransition *>(t))->_label; arg1 = (static_cast<AtomTransition *>(t))->_label;
if (arg1 == Token::_EOF) { if (arg1 == EOF) {
arg1 = 0; arg1 = 0;
arg3 = 1; arg3 = 1;
} }
@ -438,7 +438,7 @@ std::wstring ATNSerializer::decode(const std::wstring& inpdata) {
buf.append(std::to_wstring(i)).append(L":"); buf.append(std::to_wstring(i)).append(L":");
bool containsEof = data[p++] != 0; bool containsEof = data[p++] != 0;
if (containsEof) { if (containsEof) {
buf.append(getTokenName(Token::_EOF)); buf.append(getTokenName(EOF));
} }
for (int j = 0; j < nintervals; j++) { for (int j = 0; j < nintervals; j++) {

View File

@ -32,7 +32,6 @@
#include "ATNType.h" #include "ATNType.h"
#include "ATNConfigSet.h" #include "ATNConfigSet.h"
#include "DFAState.h" #include "DFAState.h"
#include "PredictionContextCache.h"
#include "ATNDeserializer.h" #include "ATNDeserializer.h"
#include "EmptyPredictionContext.h" #include "EmptyPredictionContext.h"
@ -44,27 +43,20 @@ using namespace org::antlr::v4::runtime::atn;
DFAState ATNSimulator::ERROR(INT32_MAX); DFAState ATNSimulator::ERROR(INT32_MAX);
ATNSimulator::ATNSimulator() { ATNSimulator::ATNSimulator() {
sharedContextCache = new PredictionContextCache();
} }
ATNSimulator::ATNSimulator(const ATN &atn, PredictionContextCache *sharedContextCache) ATNSimulator::ATNSimulator(const ATN &atn, std::shared_ptr<PredictionContextCache> sharedContextCache)
: atn(atn), sharedContextCache(sharedContextCache) { : atn(atn), _sharedContextCache(sharedContextCache) {
} }
PredictionContextCache *ATNSimulator::getSharedContextCache() { std::shared_ptr<PredictionContextCache> ATNSimulator::getSharedContextCache() {
return sharedContextCache; return _sharedContextCache;
} }
PredictionContext *ATNSimulator::getCachedContext(PredictionContext *context) { PredictionContextRef ATNSimulator::getCachedContext(PredictionContextRef context) {
if (sharedContextCache == nullptr) {
return context;
}
{
std::lock_guard<std::mutex> lck(mtx); std::lock_guard<std::mutex> lck(mtx);
std::map<PredictionContext*, PredictionContext*> *visited = new std::map<PredictionContext*, PredictionContext*>(); std::map<PredictionContextRef, PredictionContextRef> visited;
return PredictionContext::getCachedContext(context, sharedContextCache, visited); return PredictionContext::getCachedContext(context, _sharedContextCache, visited);
}
} }
ATN ATNSimulator::deserialize(const std::wstring &data) { ATN ATNSimulator::deserialize(const std::wstring &data) {

View File

@ -33,6 +33,7 @@
#include "ATN.h" #include "ATN.h"
#include "IntervalSet.h" #include "IntervalSet.h"
#include "PredictionContext.h"
namespace org { namespace org {
namespace antlr { namespace antlr {
@ -50,13 +51,12 @@ namespace atn {
static dfa::DFAState ERROR; static dfa::DFAState ERROR;
ATN atn; ATN atn;
ATNSimulator(const ATN &atn, PredictionContextCache *sharedContextCache); ATNSimulator(const ATN &atn, std::shared_ptr<PredictionContextCache> sharedContextCache);
virtual void reset() = 0; virtual void reset() = 0;
virtual PredictionContextCache *getSharedContextCache(); virtual std::shared_ptr<PredictionContextCache> getSharedContextCache();
virtual PredictionContextRef getCachedContext(PredictionContextRef context);
virtual PredictionContext *getCachedContext(PredictionContext *context);
/// @deprecated Use <seealso cref="ATNDeserializer#deserialize"/> instead. /// @deprecated Use <seealso cref="ATNDeserializer#deserialize"/> instead.
static ATN deserialize(const std::wstring &data); static ATN deserialize(const std::wstring &data);
@ -99,7 +99,7 @@ namespace atn {
/// more time I think and doesn't save on the overall footprint /// more time I think and doesn't save on the overall footprint
/// so it's not worth the complexity. /// so it's not worth the complexity.
/// </summary> /// </summary>
PredictionContextCache * sharedContextCache; std::shared_ptr<PredictionContextCache> _sharedContextCache;
}; };

View File

@ -36,11 +36,12 @@
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
ArrayPredictionContext::ArrayPredictionContext(SingletonPredictionContext *a) ArrayPredictionContext::ArrayPredictionContext(SingletonPredictionContextRef a)
: ArrayPredictionContext({ a->parent }, { a->returnState }) { : ArrayPredictionContext({ a->parent }, { a->returnState }) {
} }
ArrayPredictionContext::ArrayPredictionContext(const std::vector<PredictionContext *> &parents, const std::vector<int> &returnStates) ArrayPredictionContext::ArrayPredictionContext(const std::vector<std::weak_ptr<PredictionContext> > &parents,
const std::vector<int> &returnStates)
: PredictionContext(calculateHashCode(parents, returnStates)), parents(parents), returnStates(returnStates) { : PredictionContext(calculateHashCode(parents, returnStates)), parents(parents), returnStates(returnStates) {
assert(parents.size() > 0); assert(parents.size() > 0);
assert(returnStates.size() > 0); assert(returnStates.size() > 0);
@ -55,7 +56,7 @@ size_t ArrayPredictionContext::size() const {
return returnStates.size(); return returnStates.size();
} }
PredictionContext* ArrayPredictionContext::getParent(size_t index) const { std::weak_ptr<PredictionContext> ArrayPredictionContext::getParent(size_t index) const {
return parents[index]; return parents[index];
} }
@ -80,24 +81,24 @@ std::wstring ArrayPredictionContext::toString() {
if (isEmpty()) { if (isEmpty()) {
return L"[]"; return L"[]";
} }
antlrcpp::StringBuilder *buf = new antlrcpp::StringBuilder(); antlrcpp::StringBuilder buf;
buf->append(L"["); buf.append(L"[");
for (std::vector<int>::size_type i = 0; i < returnStates.size(); i++) { for (std::vector<int>::size_type i = 0; i < returnStates.size(); i++) {
if (i > 0) { if (i > 0) {
buf->append(L", "); buf.append(L", ");
} }
if (returnStates[i] == EMPTY_RETURN_STATE) { if (returnStates[i] == EMPTY_RETURN_STATE) {
buf->append(L"$"); buf.append(L"$");
continue; continue;
} }
buf->append(std::to_wstring(returnStates.at(i))); buf.append(std::to_wstring(returnStates.at(i)));
if (parents[i] != nullptr) { if (!parents[i].expired()) {
buf->append(L" "); buf.append(L" ");
buf->append(parents[i]->toString()); buf.append(parents[i].lock()->toString());
} else { } else {
buf->append(L"null"); buf.append(L"null");
} }
} }
buf->append(L"]"); buf.append(L"]");
return buf->toString(); return buf.toString();
} }

View File

@ -47,17 +47,18 @@ namespace atn {
/// Parent can be empty only if full ctx mode and we make an array /// Parent can be empty only if full ctx mode and we make an array
/// from EMPTY and non-empty. We merge EMPTY by using null parent and /// from EMPTY and non-empty. We merge EMPTY by using null parent and
/// returnState == EMPTY_RETURN_STATE. /// returnState == EMPTY_RETURN_STATE.
const std::vector<PredictionContext*> &parents; const std::vector<std::weak_ptr<PredictionContext>> parents;
/// Sorted for merge, no duplicates; if present, EMPTY_RETURN_STATE is always last. /// Sorted for merge, no duplicates; if present, EMPTY_RETURN_STATE is always last.
const std::vector<int> &returnStates; const std::vector<int> returnStates;
ArrayPredictionContext(SingletonPredictionContext *a); //this(new PredictionContext[] {a.parent}, new int[] {a.returnState}); ArrayPredictionContext(SingletonPredictionContextRef a);
ArrayPredictionContext(const std::vector<PredictionContext *> &parents, const std::vector<int> &returnStates); ArrayPredictionContext(const std::vector<std::weak_ptr<PredictionContext>> &parents,
const std::vector<int> &returnStates);
virtual bool isEmpty() const override; virtual bool isEmpty() const override;
virtual size_t size() const override; virtual size_t size() const override;
virtual PredictionContext *getParent(size_t index) const override; virtual std::weak_ptr<PredictionContext> getParent(size_t index) const override;
virtual int getReturnState(size_t index) const override; virtual int getReturnState(size_t index) const override;
bool operator == (const PredictionContext &o) const override; bool operator == (const PredictionContext &o) const override;

View File

@ -40,7 +40,7 @@ namespace runtime {
namespace atn { namespace atn {
/// <summary> /// <summary>
/// TODO: make all transitions sets? no, should remove set edges </summary> /// TO_DO: make all transitions sets? no, should remove set edges </summary>
class AtomTransition final : public Transition { class AtomTransition final : public Transition {
/// <summary> /// <summary>
/// The token type or character value; or, signifies special label. </summary> /// The token type or character value; or, signifies special label. </summary>

View File

@ -104,7 +104,7 @@ namespace atn {
} }
size_t size () const override { size_t size () const override {
return std::unordered_set<ATNConfig*, Hasher, Comparer>::size(); return Set::size();
} }
ConfigLookupIterator begin() override { ConfigLookupIterator begin() override {

View File

@ -33,7 +33,7 @@
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
EmptyPredictionContext::EmptyPredictionContext() : SingletonPredictionContext(nullptr, EMPTY_RETURN_STATE) { EmptyPredictionContext::EmptyPredictionContext() : SingletonPredictionContext(std::weak_ptr<PredictionContext>(), EMPTY_RETURN_STATE) {
} }
bool EmptyPredictionContext::isEmpty() const { bool EmptyPredictionContext::isEmpty() const {
@ -44,8 +44,8 @@ size_t EmptyPredictionContext::size() const {
return 1; return 1;
} }
org::antlr::v4::runtime::atn::PredictionContext *EmptyPredictionContext::getParent(size_t index) const { std::weak_ptr<PredictionContext> EmptyPredictionContext::getParent(size_t index) const {
return nullptr; return std::weak_ptr<PredictionContext>();
} }
int EmptyPredictionContext::getReturnState(size_t index) const { int EmptyPredictionContext::getReturnState(size_t index) const {

View File

@ -45,7 +45,7 @@ namespace atn {
virtual bool isEmpty() const override; virtual bool isEmpty() const override;
virtual size_t size() const override; virtual size_t size() const override;
virtual PredictionContext *getParent(size_t index) const override; virtual std::weak_ptr<PredictionContext> getParent(size_t index) const override;
virtual int getReturnState(size_t index) const override; virtual int getReturnState(size_t index) const override;
virtual std::wstring toString() const override; virtual std::wstring toString() const override;

View File

@ -38,6 +38,7 @@
#include "NotSetTransition.h" #include "NotSetTransition.h"
#include "IntervalSet.h" #include "IntervalSet.h"
#include "ATNConfig.h" #include "ATNConfig.h"
#include "EmptyPredictionContext.h"
#include "LL1Analyzer.h" #include "LL1Analyzer.h"
@ -56,9 +57,12 @@ std::vector<misc::IntervalSet> LL1Analyzer::getDecisionLookahead(ATNState *s) co
look.resize(s->getNumberOfTransitions()); // Fills all interval sets with defaults. look.resize(s->getNumberOfTransitions()); // Fills all interval sets with defaults.
for (size_t alt = 0; alt < s->getNumberOfTransitions(); alt++) { for (size_t alt = 0; alt < s->getNumberOfTransitions(); alt++) {
std::set<ATNConfig*> lookBusy;
bool seeThruPreds = false; // fail to get lookahead upon pred bool seeThruPreds = false; // fail to get lookahead upon pred
_LOOK(s->transition(alt)->target, nullptr, (PredictionContext*)PredictionContext::EMPTY, look[alt], lookBusy, new antlrcpp::BitSet(), seeThruPreds, false);
std::set<ATNConfig*> lookBusy;
antlrcpp::BitSet callRuleStack;
_LOOK(s->transition(alt)->target, nullptr, std::dynamic_pointer_cast<PredictionContext>(PredictionContext::EMPTY),
look[alt], lookBusy, callRuleStack, seeThruPreds, false);
// Wipe out lookahead for this alternative if we found nothing // Wipe out lookahead for this alternative if we found nothing
// or we had a predicate when we !seeThruPreds // or we had a predicate when we !seeThruPreds
@ -76,15 +80,17 @@ misc::IntervalSet LL1Analyzer::LOOK(ATNState *s, RuleContext *ctx) const {
misc::IntervalSet LL1Analyzer::LOOK(ATNState *s, ATNState *stopState, RuleContext *ctx) const { misc::IntervalSet LL1Analyzer::LOOK(ATNState *s, ATNState *stopState, RuleContext *ctx) const {
misc::IntervalSet r; misc::IntervalSet r;
bool seeThruPreds = true; // ignore preds; get all lookahead bool seeThruPreds = true; // ignore preds; get all lookahead
PredictionContext *lookContext = ctx != nullptr ? PredictionContext::fromRuleContext(*s->atn, ctx) : nullptr; PredictionContextRef lookContext = ctx != nullptr ? PredictionContext::fromRuleContext(*s->atn, ctx) : nullptr;
std::set<ATNConfig*> lookBusy; std::set<ATNConfig*> lookBusy;
_LOOK(s, stopState, lookContext, r, lookBusy, new antlrcpp::BitSet(), seeThruPreds, true); antlrcpp::BitSet callRuleStack;
_LOOK(s, stopState, lookContext, r, lookBusy, callRuleStack, seeThruPreds, true);
return r; return r;
} }
void LL1Analyzer::_LOOK(ATNState *s, ATNState *stopState, PredictionContext *ctx, misc::IntervalSet &look, void LL1Analyzer::_LOOK(ATNState *s, ATNState *stopState, PredictionContextRef ctx, misc::IntervalSet &look,
std::set<ATNConfig*> &lookBusy, antlrcpp::BitSet *calledRuleStack, bool seeThruPreds, bool addEOF) const { std::set<ATNConfig*> &lookBusy, antlrcpp::BitSet &calledRuleStack, bool seeThruPreds, bool addEOF) const {
ATNConfig *c = new ATNConfig(s, 0, ctx); ATNConfig *c = new ATNConfig(s, 0, ctx);
if (!lookBusy.insert(c).second) { if (!lookBusy.insert(c).second) {
@ -96,7 +102,7 @@ void LL1Analyzer::_LOOK(ATNState *s, ATNState *stopState, PredictionContext *ctx
look.add(Token::EPSILON); look.add(Token::EPSILON);
return; return;
} else if (ctx->isEmpty() && addEOF) { } else if (ctx->isEmpty() && addEOF) {
look.add(Token::_EOF); look.add(EOF);
return; return;
} }
} }
@ -106,26 +112,25 @@ void LL1Analyzer::_LOOK(ATNState *s, ATNState *stopState, PredictionContext *ctx
look.add(Token::EPSILON); look.add(Token::EPSILON);
return; return;
} else if (ctx->isEmpty() && addEOF) { } else if (ctx->isEmpty() && addEOF) {
look.add(Token::_EOF); look.add(EOF);
return; return;
} }
if (ctx != (PredictionContext*)PredictionContext::EMPTY) { if (ctx != PredictionContext::EMPTY) {
// run thru all possible stack tops in ctx // run thru all possible stack tops in ctx
for (size_t i = 0; i < ctx->size(); i++) { for (size_t i = 0; i < ctx->size(); i++) {
ATNState *returnState = _atn.states[(size_t)ctx->getReturnState(i)]; ATNState *returnState = _atn.states[(size_t)ctx->getReturnState(i)];
// System.out.println("popping back to "+retState);
bool removed = calledRuleStack->data.test((size_t)returnState->ruleIndex); bool removed = calledRuleStack.data.test((size_t)returnState->ruleIndex);
try { try {
calledRuleStack->data[(size_t)returnState->ruleIndex] = false; calledRuleStack.data[(size_t)returnState->ruleIndex] = false;
_LOOK(returnState, stopState, ctx->getParent(i), look, lookBusy, calledRuleStack, seeThruPreds, addEOF); _LOOK(returnState, stopState, ctx->getParent(i).lock(), look, lookBusy, calledRuleStack, seeThruPreds, addEOF);
} }
catch(...) { catch(...) {
// Just move to the next steps as a "finally" clause // Just move to the next steps as a "finally" clause
} }
if (removed) { if (removed) {
calledRuleStack->set((size_t)returnState->ruleIndex); calledRuleStack.set((size_t)returnState->ruleIndex);
} }
} }
@ -138,20 +143,20 @@ void LL1Analyzer::_LOOK(ATNState *s, ATNState *stopState, PredictionContext *ctx
Transition *t = s->transition(i); Transition *t = s->transition(i);
if (typeid(t) == typeid(RuleTransition)) { if (typeid(t) == typeid(RuleTransition)) {
if ( (*calledRuleStack).data[(size_t)(static_cast<RuleTransition*>(t))->target->ruleIndex]) { if (calledRuleStack.data[(size_t)(static_cast<RuleTransition*>(t))->target->ruleIndex]) {
continue; continue;
} }
PredictionContext *newContext = SingletonPredictionContext::create(ctx, (static_cast<RuleTransition*>(t))->followState->stateNumber); PredictionContextRef newContext = SingletonPredictionContext::create(ctx, (static_cast<RuleTransition*>(t))->followState->stateNumber);
try { try {
calledRuleStack->set((size_t)(static_cast<RuleTransition*>(t))->target->ruleIndex); calledRuleStack.set((size_t)(static_cast<RuleTransition*>(t))->target->ruleIndex);
_LOOK(t->target, stopState, newContext, look, lookBusy, calledRuleStack, seeThruPreds, addEOF); _LOOK(t->target, stopState, newContext, look, lookBusy, calledRuleStack, seeThruPreds, addEOF);
} }
catch(...) { catch(...) {
// Just move to the next steps as a "finally" clause // Just move to the next steps as a "finally" clause
} }
calledRuleStack->data[(size_t)((static_cast<RuleTransition*>(t))->target->ruleIndex)] = false; calledRuleStack.data[(size_t)((static_cast<RuleTransition*>(t))->target->ruleIndex)] = false;
} else if (dynamic_cast<AbstractPredicateTransition*>(t) != nullptr) { } else if (dynamic_cast<AbstractPredicateTransition*>(t) != nullptr) {
if (seeThruPreds) { if (seeThruPreds) {

View File

@ -33,6 +33,7 @@
#include "Token.h" #include "Token.h"
#include "BitSet.h" #include "BitSet.h"
#include "PredictionContext.h"
namespace org { namespace org {
namespace antlr { namespace antlr {
@ -129,8 +130,8 @@ namespace atn {
/// outermost context is reached. This parameter has no effect if {@code ctx} /// outermost context is reached. This parameter has no effect if {@code ctx}
/// is {@code null}. </param> /// is {@code null}. </param>
protected: protected:
virtual void _LOOK(ATNState *s, ATNState *stopState, PredictionContext *ctx, misc::IntervalSet &look, virtual void _LOOK(ATNState *s, ATNState *stopState, PredictionContextRef ctx, misc::IntervalSet &look,
std::set<ATNConfig*> &lookBusy, antlrcpp::BitSet *calledRuleStack, bool seeThruPreds, bool addEOF) const; std::set<ATNConfig*> &lookBusy, antlrcpp::BitSet &calledRuleStack, bool seeThruPreds, bool addEOF) const;
}; };
} // namespace atn } // namespace atn

View File

@ -37,28 +37,28 @@
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
LexerATNConfig::LexerATNConfig(ATNState *state, int alt, PredictionContext *context) : ATNConfig(state, alt, context, SemanticContext::NONE), passedThroughNonGreedyDecision(false) { LexerATNConfig::LexerATNConfig(ATNState *state, int alt, PredictionContextRef context)
InitializeInstanceFields(); : ATNConfig(state, alt, context, SemanticContext::NONE), passedThroughNonGreedyDecision(false) {
} }
LexerATNConfig::LexerATNConfig(ATNState *state, int alt, PredictionContext *context, int actionIndex) : ATNConfig(state, alt, context, SemanticContext::NONE), passedThroughNonGreedyDecision(false) { LexerATNConfig::LexerATNConfig(ATNState *state, int alt, PredictionContextRef context, int actionIndex)
InitializeInstanceFields(); : ATNConfig(state, alt, context, SemanticContext::NONE), passedThroughNonGreedyDecision(false) {
this->lexerActionIndex = actionIndex; lexerActionIndex = actionIndex;
} }
LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state) : ATNConfig(c, state, c->context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) { LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state)
InitializeInstanceFields(); : ATNConfig(c, state, c->context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) {
this->lexerActionIndex = c->lexerActionIndex; lexerActionIndex = c->lexerActionIndex;
} }
LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state, int actionIndex) : ATNConfig(c, state, c->context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) { LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state, int actionIndex)
InitializeInstanceFields(); : ATNConfig(c, state, c->context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) {
this->lexerActionIndex = actionIndex; lexerActionIndex = actionIndex;
} }
LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state, PredictionContext *context) : ATNConfig(c, state, context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) { LexerATNConfig::LexerATNConfig(LexerATNConfig *c, ATNState *state, PredictionContextRef context)
InitializeInstanceFields(); : ATNConfig(c, state, context, c->semanticContext), passedThroughNonGreedyDecision(checkNonGreedyDecision(c, state)) {
this->lexerActionIndex = c->lexerActionIndex; lexerActionIndex = c->lexerActionIndex;
} }
bool LexerATNConfig::hasPassedThroughNonGreedyDecision() { bool LexerATNConfig::hasPassedThroughNonGreedyDecision() {
@ -69,8 +69,8 @@ size_t LexerATNConfig::hashCode() const {
size_t hashCode = misc::MurmurHash::initialize(7); size_t hashCode = misc::MurmurHash::initialize(7);
hashCode = misc::MurmurHash::update(hashCode, (size_t)state->stateNumber); hashCode = misc::MurmurHash::update(hashCode, (size_t)state->stateNumber);
hashCode = misc::MurmurHash::update(hashCode, (size_t)alt); hashCode = misc::MurmurHash::update(hashCode, (size_t)alt);
hashCode = misc::MurmurHash::update(hashCode, (size_t)context); hashCode = misc::MurmurHash::update(hashCode, (size_t)context.get());
hashCode = misc::MurmurHash::update(hashCode, (size_t)semanticContext); hashCode = misc::MurmurHash::update(hashCode, (size_t)semanticContext.get());
hashCode = misc::MurmurHash::update(hashCode, passedThroughNonGreedyDecision ? 1 : 0); hashCode = misc::MurmurHash::update(hashCode, passedThroughNonGreedyDecision ? 1 : 0);
hashCode = misc::MurmurHash::finish(hashCode, 5); hashCode = misc::MurmurHash::finish(hashCode, 5);
return hashCode; return hashCode;
@ -81,13 +81,10 @@ bool LexerATNConfig::operator == (const LexerATNConfig& other) const
if (passedThroughNonGreedyDecision != other.passedThroughNonGreedyDecision) if (passedThroughNonGreedyDecision != other.passedThroughNonGreedyDecision)
return false; return false;
return ATNConfig::operator==(other); return ATNConfig::operator == (other);
} }
bool LexerATNConfig::checkNonGreedyDecision(LexerATNConfig *source, ATNState *target) { bool LexerATNConfig::checkNonGreedyDecision(LexerATNConfig *source, ATNState *target) {
return source->passedThroughNonGreedyDecision || (dynamic_cast<DecisionState*>(target) != nullptr && (static_cast<DecisionState*>(target))->nonGreedy); return source->passedThroughNonGreedyDecision ||
} (dynamic_cast<DecisionState*>(target) != nullptr && (static_cast<DecisionState*>(target))->nonGreedy);
void LexerATNConfig::InitializeInstanceFields() {
lexerActionIndex = -1;
} }

View File

@ -40,24 +40,16 @@ namespace runtime {
namespace atn { namespace atn {
class LexerATNConfig : public ATNConfig { class LexerATNConfig : public ATNConfig {
/// <summary>
/// Capture lexer action we traverse </summary>
public: public:
int lexerActionIndex; /// Capture lexer action we traverse.
int lexerActionIndex = -1;
private: LexerATNConfig(ATNState *state, int alt, PredictionContextRef context);
const bool passedThroughNonGreedyDecision; LexerATNConfig(ATNState *state, int alt, PredictionContextRef context, int actionIndex);
public:
LexerATNConfig(ATNState *state, int alt, PredictionContext *context);
LexerATNConfig(ATNState *state, int alt, PredictionContext *context, int actionIndex);
LexerATNConfig(LexerATNConfig *c, ATNState *state); LexerATNConfig(LexerATNConfig *c, ATNState *state);
LexerATNConfig(LexerATNConfig *c, ATNState *state, int actionIndex); LexerATNConfig(LexerATNConfig *c, ATNState *state, int actionIndex);
LexerATNConfig(LexerATNConfig *c, ATNState *state, PredictionContextRef context);
LexerATNConfig(LexerATNConfig *c, ATNState *state, PredictionContext *context);
bool hasPassedThroughNonGreedyDecision(); bool hasPassedThroughNonGreedyDecision();
@ -66,10 +58,9 @@ namespace atn {
bool operator == (const LexerATNConfig& other) const; bool operator == (const LexerATNConfig& other) const;
private: private:
static bool checkNonGreedyDecision(LexerATNConfig *source, ATNState *target); const bool passedThroughNonGreedyDecision;
private: static bool checkNonGreedyDecision(LexerATNConfig *source, ATNState *target);
void InitializeInstanceFields();
}; };
} // namespace atn } // namespace atn

View File

@ -44,6 +44,7 @@
#include "DFAState.h" #include "DFAState.h"
#include "LexerATNConfig.h" #include "LexerATNConfig.h"
#include "EmptyPredictionContext.h"
#include "LexerATNSimulator.h" #include "LexerATNSimulator.h"
@ -54,9 +55,7 @@ void LexerATNSimulator::SimState::reset() {
index = -1; index = -1;
line = 0; line = 0;
charPos = -1; charPos = -1;
// TODO: Memory Management - delete dfaState = nullptr; // Don't delete. It's just a reference.
delete dfaState;
dfaState = nullptr;
} }
void LexerATNSimulator::SimState::InitializeInstanceFields() { void LexerATNSimulator::SimState::InitializeInstanceFields() {
@ -68,12 +67,14 @@ void LexerATNSimulator::SimState::InitializeInstanceFields() {
int LexerATNSimulator::match_calls = 0; int LexerATNSimulator::match_calls = 0;
LexerATNSimulator::LexerATNSimulator(const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA, PredictionContextCache *sharedContextCache) LexerATNSimulator::LexerATNSimulator(const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA,
std::shared_ptr<PredictionContextCache> sharedContextCache)
: LexerATNSimulator(nullptr, atn, decisionToDFA, sharedContextCache) { : LexerATNSimulator(nullptr, atn, decisionToDFA, sharedContextCache) {
} }
LexerATNSimulator::LexerATNSimulator(Lexer *recog, const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA, PredictionContextCache *sharedContextCache) LexerATNSimulator::LexerATNSimulator(Lexer *recog, const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA,
: ATNSimulator(atn, sharedContextCache), _recog(recog), _decisionToDFA(decisionToDFA), prevAccept(new SimState()) { std::shared_ptr<PredictionContextCache> sharedContextCache)
: ATNSimulator(atn, sharedContextCache), _recog(recog), _decisionToDFA(decisionToDFA), prevAccept(new SimState()) {
InitializeInstanceFields(); InitializeInstanceFields();
} }
@ -146,7 +147,7 @@ int LexerATNSimulator::execATN(CharStream *input, dfa::DFAState *ds0) {
std::wcout << L"start state closure=" << ds0->configs << std::endl; std::wcout << L"start state closure=" << ds0->configs << std::endl;
} }
size_t t = input->LA(1); ssize_t t = input->LA(1);
dfa::DFAState *s = ds0; // s is current/from DFA state dfa::DFAState *s = ds0; // s is current/from DFA state
while (true) { // while more work while (true) { // while more work
@ -182,12 +183,12 @@ int LexerATNSimulator::execATN(CharStream *input, dfa::DFAState *ds0) {
if (target->isAcceptState) { if (target->isAcceptState) {
captureSimState(prevAccept, input, target); captureSimState(prevAccept, input, target);
if (t == IntStream::_EOF) { if (t == EOF) {
break; break;
} }
} }
if (t != IntStream::_EOF) { if (t != EOF) {
consume(input); consume(input);
t = input->LA(1); t = input->LA(1);
} }
@ -198,12 +199,12 @@ int LexerATNSimulator::execATN(CharStream *input, dfa::DFAState *ds0) {
return failOrAccept(prevAccept, input, s->configs, t); return failOrAccept(prevAccept, input, s->configs, t);
} }
dfa::DFAState *LexerATNSimulator::getExistingTargetState(dfa::DFAState *s, size_t t) { dfa::DFAState *LexerATNSimulator::getExistingTargetState(dfa::DFAState *s, ssize_t t) {
if (s->edges.size() == 0 || /*t < MIN_DFA_EDGE ||*/ t > MAX_DFA_EDGE) { if (s->edges.size() == 0 || t < MIN_DFA_EDGE || t > MAX_DFA_EDGE) {
return nullptr; return nullptr;
} }
dfa::DFAState *target = s->edges[t - MIN_DFA_EDGE]; dfa::DFAState *target = s->edges[(size_t)(t - MIN_DFA_EDGE)];
if (debug && target != nullptr) { if (debug && target != nullptr) {
std::wcout << std::wstring(L"reuse state ") << s->stateNumber << std::wstring(L" edge to ") << target->stateNumber << std::endl; std::wcout << std::wstring(L"reuse state ") << s->stateNumber << std::wstring(L" edge to ") << target->stateNumber << std::endl;
} }
@ -211,7 +212,7 @@ dfa::DFAState *LexerATNSimulator::getExistingTargetState(dfa::DFAState *s, size_
return target; return target;
} }
dfa::DFAState *LexerATNSimulator::computeTargetState(CharStream *input, dfa::DFAState *s, size_t t) { dfa::DFAState *LexerATNSimulator::computeTargetState(CharStream *input, dfa::DFAState *s, ssize_t t) {
OrderedATNConfigSet *reach = new OrderedATNConfigSet(); OrderedATNConfigSet *reach = new OrderedATNConfigSet();
// if we don't find an existing DFA state // if we don't find an existing DFA state
@ -230,7 +231,7 @@ dfa::DFAState *LexerATNSimulator::computeTargetState(CharStream *input, dfa::DFA
return addDFAEdge(s, t, reach); return addDFAEdge(s, t, reach);
} }
int LexerATNSimulator::failOrAccept(SimState *prevAccept, CharStream *input, ATNConfigSet *reach, size_t t) { int LexerATNSimulator::failOrAccept(SimState *prevAccept, CharStream *input, ATNConfigSet *reach, ssize_t t) {
if (prevAccept->dfaState != nullptr) { if (prevAccept->dfaState != nullptr) {
int ruleIndex = prevAccept->dfaState->lexerRuleIndex; int ruleIndex = prevAccept->dfaState->lexerRuleIndex;
int actionIndex = prevAccept->dfaState->lexerActionIndex; int actionIndex = prevAccept->dfaState->lexerActionIndex;
@ -238,18 +239,19 @@ int LexerATNSimulator::failOrAccept(SimState *prevAccept, CharStream *input, ATN
return prevAccept->dfaState->prediction; return prevAccept->dfaState->prediction;
} else { } else {
// if no accept and EOF is first char, return EOF // if no accept and EOF is first char, return EOF
if (t == IntStream::_EOF && input->index() == (size_t)_startIndex) { if (t == EOF && input->index() == (size_t)_startIndex) {
return Token::_EOF; return EOF;
} }
throw LexerNoViableAltException(_recog, input, (size_t)_startIndex, reach); throw LexerNoViableAltException(_recog, input, (size_t)_startIndex, reach);
} }
} }
void LexerATNSimulator::getReachableConfigSet(CharStream *input, ATNConfigSet *closure, ATNConfigSet *reach, size_t t) { void LexerATNSimulator::getReachableConfigSet(CharStream *input, ATNConfigSet *closure, ATNConfigSet *reach, ssize_t t) {
// this is used to skip processing for configs which have a lower priority // this is used to skip processing for configs which have a lower priority
// than a config that already reached an accept state for the same rule // than a config that already reached an accept state for the same rule
int skipAlt = ATN::INVALID_ALT_NUMBER; int skipAlt = ATN::INVALID_ALT_NUMBER;
if (closure->configLookup) {
for (auto c : *closure->configLookup) { for (auto c : *closure->configLookup) {
bool currentAltReachedAcceptState = c->alt == skipAlt; bool currentAltReachedAcceptState = c->alt == skipAlt;
if (currentAltReachedAcceptState && (static_cast<LexerATNConfig*>(c))->hasPassedThroughNonGreedyDecision()) { if (currentAltReachedAcceptState && (static_cast<LexerATNConfig*>(c))->hasPassedThroughNonGreedyDecision()) {
@ -274,6 +276,7 @@ void LexerATNSimulator::getReachableConfigSet(CharStream *input, ATNConfigSet *c
} }
} }
} }
}
} }
void LexerATNSimulator::accept(CharStream *input, int ruleIndex, int actionIndex, size_t index, size_t line, size_t charPos) { void LexerATNSimulator::accept(CharStream *input, int ruleIndex, int actionIndex, size_t index, size_t line, size_t charPos) {
@ -295,13 +298,13 @@ void LexerATNSimulator::accept(CharStream *input, int ruleIndex, int actionIndex
input->seek(index); input->seek(index);
_line = line; _line = line;
_charPositionInLine = (int)charPos; _charPositionInLine = (int)charPos;
if (input->LA(1) != IntStream::_EOF) { if (input->LA(1) != EOF) {
consume(input); consume(input);
} }
} }
atn::ATNState *LexerATNSimulator::getReachableTarget(Transition *trans, int t) { atn::ATNState *LexerATNSimulator::getReachableTarget(Transition *trans, ssize_t t) {
if (trans->matches(t, WCHAR_MIN, WCHAR_MAX)) { if (trans->matches((int)t, WCHAR_MIN, WCHAR_MAX)) {
return trans->target; return trans->target;
} }
@ -309,17 +312,18 @@ atn::ATNState *LexerATNSimulator::getReachableTarget(Transition *trans, int t) {
} }
atn::ATNConfigSet *LexerATNSimulator::computeStartState(CharStream *input, ATNState *p) { atn::ATNConfigSet *LexerATNSimulator::computeStartState(CharStream *input, ATNState *p) {
EmptyPredictionContext * initialContext = PredictionContext::EMPTY; std::shared_ptr<EmptyPredictionContext> initialContext = PredictionContext::EMPTY; // ml: the purpose of this assignment is unclear
ATNConfigSet *configs = new OrderedATNConfigSet(); ATNConfigSet *configs = new OrderedATNConfigSet();
for (size_t i = 0; i < p->getNumberOfTransitions(); i++) { for (size_t i = 0; i < p->getNumberOfTransitions(); i++) {
ATNState *target = p->transition(i)->target; ATNState *target = p->transition(i)->target;
LexerATNConfig *c = new LexerATNConfig(target, (int)(i + 1), (PredictionContext*)initialContext); LexerATNConfig *c = new LexerATNConfig(target, (int)(i + 1), std::dynamic_pointer_cast<PredictionContext>(initialContext));
closure(input, c, configs, false, false); closure(input, c, configs, false, false);
} }
return configs; return configs;
} }
bool LexerATNSimulator::closure(CharStream *input, LexerATNConfig *config, ATNConfigSet *configs, bool currentAltReachedAcceptState, bool speculative) { bool LexerATNSimulator::closure(CharStream *input, LexerATNConfig *config, ATNConfigSet *configs,
bool currentAltReachedAcceptState, bool speculative) {
if (debug) { if (debug) {
std::wcout << L"closure(" << config->toString(true) << L")" << std::endl; std::wcout << L"closure(" << config->toString(true) << L")" << std::endl;
} }
@ -338,7 +342,7 @@ bool LexerATNSimulator::closure(CharStream *input, LexerATNConfig *config, ATNCo
configs->add(config); configs->add(config);
return true; return true;
} else { } else {
configs->add(new LexerATNConfig(config, config->state, (PredictionContext*)PredictionContext::EMPTY)); configs->add(new LexerATNConfig(config, config->state, std::dynamic_pointer_cast<PredictionContext>(PredictionContext::EMPTY)));
currentAltReachedAcceptState = true; currentAltReachedAcceptState = true;
} }
} }
@ -346,9 +350,9 @@ bool LexerATNSimulator::closure(CharStream *input, LexerATNConfig *config, ATNCo
if (config->context != nullptr && !config->context->isEmpty()) { if (config->context != nullptr && !config->context->isEmpty()) {
for (size_t i = 0; i < config->context->size(); i++) { for (size_t i = 0; i < config->context->size(); i++) {
if (config->context->getReturnState(i) != PredictionContext::EMPTY_RETURN_STATE) { if (config->context->getReturnState(i) != PredictionContext::EMPTY_RETURN_STATE) {
PredictionContext *newContext = config->context->getParent(i); // "pop" return state std::weak_ptr<PredictionContext> newContext = config->context->getParent(i); // "pop" return state
ATNState *returnState = atn.states[(size_t)config->context->getReturnState(i)]; ATNState *returnState = atn.states[(size_t)config->context->getReturnState(i)];
LexerATNConfig *c = new LexerATNConfig(returnState, config->alt, newContext); LexerATNConfig *c = new LexerATNConfig(returnState, config->alt, newContext.lock());
currentAltReachedAcceptState = closure(input, c, configs, currentAltReachedAcceptState, speculative); currentAltReachedAcceptState = closure(input, c, configs, currentAltReachedAcceptState, speculative);
} }
} }
@ -381,16 +385,13 @@ atn::LexerATNConfig *LexerATNSimulator::getEpsilonTarget(CharStream *input, Lexe
switch (t->getSerializationType()) { switch (t->getSerializationType()) {
case Transition::RULE: { case Transition::RULE: {
RuleTransition *ruleTransition = static_cast<RuleTransition*>(t); RuleTransition *ruleTransition = static_cast<RuleTransition*>(t);
PredictionContext *newContext = SingletonPredictionContext::create(config->context, ruleTransition->followState->stateNumber); PredictionContextRef newContext = SingletonPredictionContext::create(config->context, ruleTransition->followState->stateNumber);
c = new LexerATNConfig(config, t->target, newContext); c = new LexerATNConfig(config, t->target, newContext);
} }
break; break;
case Transition::PRECEDENCE: case Transition::PRECEDENCE:
//{ throw UnsupportedOperationException("Precedence predicates are not supported in lexers.");
throw new UnsupportedOperationException("Precedence predicates are not supported in lexers.");
//}
break;
case Transition::PREDICATE: { case Transition::PREDICATE: {
/* Track traversing semantic predicates. If we traverse, /* Track traversing semantic predicates. If we traverse,
@ -466,7 +467,7 @@ void LexerATNSimulator::captureSimState(SimState *settings, CharStream *input, d
settings->dfaState = dfaState; settings->dfaState = dfaState;
} }
dfa::DFAState *LexerATNSimulator::addDFAEdge(dfa::DFAState *from, size_t t, ATNConfigSet *q) { dfa::DFAState *LexerATNSimulator::addDFAEdge(dfa::DFAState *from, ssize_t t, ATNConfigSet *q) {
/* leading to this call, ATNConfigSet.hasSemanticContext is used as a /* leading to this call, ATNConfigSet.hasSemanticContext is used as a
* marker indicating dynamic predicate evaluation makes this edge * marker indicating dynamic predicate evaluation makes this edge
* dependent on the specific input sequence, so the static edge in the * dependent on the specific input sequence, so the static edge in the
@ -491,8 +492,8 @@ dfa::DFAState *LexerATNSimulator::addDFAEdge(dfa::DFAState *from, size_t t, ATNC
return to; return to;
} }
void LexerATNSimulator::addDFAEdge(dfa::DFAState *p, size_t t, dfa::DFAState *q) { void LexerATNSimulator::addDFAEdge(dfa::DFAState *p, ssize_t t, dfa::DFAState *q) {
if (/*t < MIN_DFA_EDGE ||*/ t > MAX_DFA_EDGE) { if (t < MIN_DFA_EDGE || t > MAX_DFA_EDGE) {
// Only track edges within the DFA bounds // Only track edges within the DFA bounds
return; return;
} }
@ -506,7 +507,7 @@ void LexerATNSimulator::addDFAEdge(dfa::DFAState *p, size_t t, dfa::DFAState *q)
// make room for tokens 1..n and -1 masquerading as index 0 // make room for tokens 1..n and -1 masquerading as index 0
p->edges.resize(MAX_DFA_EDGE - MIN_DFA_EDGE + 1); p->edges.resize(MAX_DFA_EDGE - MIN_DFA_EDGE + 1);
} }
p->edges[t - MIN_DFA_EDGE] = q; // connect p->edges[(size_t)(t - MIN_DFA_EDGE)] = q; // connect
} }
dfa::DFAState *LexerATNSimulator::addDFAState(ATNConfigSet *configs) { dfa::DFAState *LexerATNSimulator::addDFAState(ATNConfigSet *configs) {
@ -536,9 +537,9 @@ dfa::DFAState *LexerATNSimulator::addDFAState(ATNConfigSet *configs) {
{ {
std::lock_guard<std::mutex> lck(mtx); std::lock_guard<std::mutex> lck(mtx);
dfa::DFAState *existing = dfa->states->at(proposed); auto iterator = dfa->states->find(proposed);
if (existing != nullptr) { if (iterator != dfa->states->end()) {
return existing; return iterator->second;
} }
dfa::DFAState *newState = proposed; dfa::DFAState *newState = proposed;
@ -546,7 +547,7 @@ dfa::DFAState *LexerATNSimulator::addDFAState(ATNConfigSet *configs) {
newState->stateNumber = (int)dfa->states->size(); newState->stateNumber = (int)dfa->states->size();
configs->setReadonly(true); configs->setReadonly(true);
newState->configs = configs; newState->configs = configs;
dfa->states->emplace(newState, newState); (*dfa->states)[newState] = newState;
return newState; return newState;
} }
} }
@ -577,7 +578,7 @@ void LexerATNSimulator::setCharPositionInLine(int charPositionInLine) {
} }
void LexerATNSimulator::consume(CharStream *input) { void LexerATNSimulator::consume(CharStream *input) {
size_t curChar = input->LA(1); ssize_t curChar = input->LA(1);
if (curChar == L'\n') { if (curChar == L'\n') {
_line++; _line++;
_charPositionInLine = 0; _charPositionInLine = 0;

View File

@ -115,8 +115,9 @@ namespace atn {
public: public:
static int match_calls; static int match_calls;
LexerATNSimulator(const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA, PredictionContextCache *sharedContextCache); LexerATNSimulator(const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA, std::shared_ptr<PredictionContextCache> sharedContextCache);
LexerATNSimulator(Lexer *recog, const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA, PredictionContextCache *sharedContextCache); LexerATNSimulator(Lexer *recog, const ATN &atn, const std::vector<dfa::DFA*> &decisionToDFA,
std::shared_ptr<PredictionContextCache> sharedContextCache);
virtual void copyState(LexerATNSimulator *simulator); virtual void copyState(LexerATNSimulator *simulator);
@ -139,7 +140,7 @@ namespace atn {
/// <returns> The existing target DFA state for the given input symbol /// <returns> The existing target DFA state for the given input symbol
/// {@code t}, or {@code null} if the target state for this edge is not /// {@code t}, or {@code null} if the target state for this edge is not
/// already cached </returns> /// already cached </returns>
virtual dfa::DFAState *getExistingTargetState(dfa::DFAState *s, size_t t); virtual dfa::DFAState *getExistingTargetState(dfa::DFAState *s, ssize_t t);
/// <summary> /// <summary>
/// Compute a target state for an edge in the DFA, and attempt to add the /// Compute a target state for an edge in the DFA, and attempt to add the
@ -152,20 +153,20 @@ namespace atn {
/// <returns> The computed target DFA state for the given input symbol /// <returns> The computed target DFA state for the given input symbol
/// {@code t}. If {@code t} does not lead to a valid DFA state, this method /// {@code t}. If {@code t} does not lead to a valid DFA state, this method
/// returns <seealso cref="#ERROR"/>. </returns> /// returns <seealso cref="#ERROR"/>. </returns>
virtual dfa::DFAState *computeTargetState(CharStream *input, dfa::DFAState *s, size_t t); virtual dfa::DFAState *computeTargetState(CharStream *input, dfa::DFAState *s, ssize_t t);
virtual int failOrAccept(SimState *prevAccept, CharStream *input, ATNConfigSet *reach, size_t t); virtual int failOrAccept(SimState *prevAccept, CharStream *input, ATNConfigSet *reach, ssize_t t);
/// <summary> /// <summary>
/// Given a starting configuration set, figure out all ATN configurations /// Given a starting configuration set, figure out all ATN configurations
/// we can reach upon input {@code t}. Parameter {@code reach} is a return /// we can reach upon input {@code t}. Parameter {@code reach} is a return
/// parameter. /// parameter.
/// </summary> /// </summary>
void getReachableConfigSet(CharStream *input, ATNConfigSet *closure, ATNConfigSet *reach, size_t t); void getReachableConfigSet(CharStream *input, ATNConfigSet *closure, ATNConfigSet *reach, ssize_t t);
virtual void accept(CharStream *input, int ruleIndex, int actionIndex, size_t index, size_t line, size_t charPos); virtual void accept(CharStream *input, int ruleIndex, int actionIndex, size_t index, size_t line, size_t charPos);
virtual ATNState *getReachableTarget(Transition *trans, int t); virtual ATNState *getReachableTarget(Transition *trans, ssize_t t);
virtual atn::ATNConfigSet *computeStartState(CharStream *input, ATNState *p); virtual atn::ATNConfigSet *computeStartState(CharStream *input, ATNState *p);
@ -206,10 +207,8 @@ namespace atn {
virtual bool evaluatePredicate(CharStream *input, int ruleIndex, int predIndex, bool speculative); virtual bool evaluatePredicate(CharStream *input, int ruleIndex, int predIndex, bool speculative);
virtual void captureSimState(SimState *settings, CharStream *input, dfa::DFAState *dfaState); virtual void captureSimState(SimState *settings, CharStream *input, dfa::DFAState *dfaState);
virtual dfa::DFAState *addDFAEdge(dfa::DFAState *from, ssize_t t, ATNConfigSet *q);
virtual dfa::DFAState *addDFAEdge(dfa::DFAState *from, size_t t, ATNConfigSet *q); virtual void addDFAEdge(dfa::DFAState *p, ssize_t t, dfa::DFAState *q);
virtual void addDFAEdge(dfa::DFAState *p, size_t t, dfa::DFAState *q);
/// <summary> /// <summary>
/// Add a new DFA state if there isn't one with this set of /// Add a new DFA state if there isn't one with this set of

View File

@ -34,5 +34,5 @@
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
OrderedATNConfigSet::OrderedATNConfigSet() OrderedATNConfigSet::OrderedATNConfigSet()
: ATNConfigSet(new ConfigLookupImpl<OrderedATNConfigHasher, OrderedATNConfigComparer>()) { : ATNConfigSet(true, std::shared_ptr<ConfigLookup>(new ConfigLookupImpl<OrderedATNConfigHasher, OrderedATNConfigComparer>())) {
} }

View File

@ -46,7 +46,6 @@
#include "PredicateTransition.h" #include "PredicateTransition.h"
#include "PrecedencePredicateTransition.h" #include "PrecedencePredicateTransition.h"
#include "ActionTransition.h" #include "ActionTransition.h"
#include "DoubleKeyMap.h"
#include "RuleStopState.h" #include "RuleStopState.h"
#include "ATNConfigSet.h" #include "ATNConfigSet.h"
#include "ATNConfig.h" #include "ATNConfig.h"
@ -63,13 +62,13 @@ using namespace org::antlr::v4::runtime::atn;
using namespace antlrcpp; using namespace antlrcpp;
ParserATNSimulator::ParserATNSimulator(const ATN &atn, const std::vector<dfa::DFA *>& decisionToDFA, ParserATNSimulator::ParserATNSimulator(const ATN &atn, const std::vector<dfa::DFA *> &decisionToDFA,
PredictionContextCache *sharedContextCache) std::shared_ptr<PredictionContextCache> sharedContextCache)
: ParserATNSimulator(nullptr, atn, decisionToDFA, sharedContextCache) { : ParserATNSimulator(nullptr, atn, decisionToDFA, sharedContextCache) {
} }
ParserATNSimulator::ParserATNSimulator(Parser *parser, const ATN &atn, const std::vector<dfa::DFA *>& decisionToDFA, ParserATNSimulator::ParserATNSimulator(Parser *parser, const ATN &atn, const std::vector<dfa::DFA *> &decisionToDFA,
PredictionContextCache *sharedContextCache) std::shared_ptr<PredictionContextCache> sharedContextCache)
: ATNSimulator(atn, sharedContextCache), parser(parser), _decisionToDFA(decisionToDFA) { : ATNSimulator(atn, sharedContextCache), parser(parser), _decisionToDFA(decisionToDFA) {
InitializeInstanceFields(); InitializeInstanceFields();
} }
@ -117,7 +116,7 @@ int ParserATNSimulator::adaptivePredict(TokenStream *input, int decision, Parser
// Do nothing, failed predict // Do nothing, failed predict
} }
delete mergeCache; // wack cache after each prediction mergeCache.clear(); // wack cache after each prediction
input->seek(index); input->seek(index);
input->release(m); input->release(m);
@ -136,7 +135,7 @@ int ParserATNSimulator::execATN(dfa::DFA *dfa, dfa::DFAState *s0, TokenStream *i
std::wcout << L"s0 = " << s0 << std::endl; std::wcout << L"s0 = " << s0 << std::endl;
} }
size_t t = input->LA(1); ssize_t t = input->LA(1);
while (true) { // while more work while (true) { // while more work
dfa::DFAState *D = getExistingTargetState(previousD, t); dfa::DFAState *D = getExistingTargetState(previousD, t);
@ -225,23 +224,23 @@ int ParserATNSimulator::execATN(dfa::DFA *dfa, dfa::DFAState *s0, TokenStream *i
previousD = D; previousD = D;
if (t != IntStream::_EOF) { if (t != EOF) {
input->consume(); input->consume();
t = input->LA(1); t = input->LA(1);
} }
} }
} }
dfa::DFAState *ParserATNSimulator::getExistingTargetState(dfa::DFAState *previousD, size_t t) { dfa::DFAState *ParserATNSimulator::getExistingTargetState(dfa::DFAState *previousD, ssize_t t) {
std::vector<dfa::DFAState *> edges = previousD->edges; std::vector<dfa::DFAState *> edges = previousD->edges;
if (edges.size() == 0 || /*t + 1 < 0 ||*/ t + 1 >= edges.size()) { if (edges.size() == 0 || t + 1 < 0 || t + 1 >= (ssize_t)edges.size()) {
return nullptr; return nullptr;
} }
return edges[t + 1]; return edges[(size_t)t + 1];
} }
dfa::DFAState *ParserATNSimulator::computeTargetState(dfa::DFA *dfa, dfa::DFAState *previousD, size_t t) { dfa::DFAState *ParserATNSimulator::computeTargetState(dfa::DFA *dfa, dfa::DFAState *previousD, ssize_t t) {
ATNConfigSet *reach = computeReachSet(previousD->configs, t, false); ATNConfigSet *reach = computeReachSet(previousD->configs, t, false);
if (reach == nullptr) { if (reach == nullptr) {
addDFAEdge(dfa, previousD, t, &ERROR); addDFAEdge(dfa, previousD, t, &ERROR);
@ -299,7 +298,7 @@ void ParserATNSimulator::predicateDFAState(dfa::DFAState *dfaState, DecisionStat
// pairs if preds found for conflicting alts // pairs if preds found for conflicting alts
BitSet *altsToCollectPredsFrom = nullptr; BitSet *altsToCollectPredsFrom = nullptr;
altsToCollectPredsFrom->data = getConflictingAltsOrUniqueAlt(dfaState->configs).data; altsToCollectPredsFrom->data = getConflictingAltsOrUniqueAlt(dfaState->configs).data;
std::vector<SemanticContext*> altToPred = getPredsForAmbigAlts(altsToCollectPredsFrom, dfaState->configs, nalts); std::vector<SemanticContextRef> altToPred = getPredsForAmbigAlts(altsToCollectPredsFrom, dfaState->configs, nalts);
if (!altToPred.empty()) { if (!altToPred.empty()) {
dfaState->predicates = getPredicatePredictions(altsToCollectPredsFrom, altToPred); dfaState->predicates = getPredicatePredictions(altsToCollectPredsFrom, altToPred);
dfaState->prediction = ATN::INVALID_ALT_NUMBER; // make sure we use preds dfaState->prediction = ATN::INVALID_ALT_NUMBER; // make sure we use preds
@ -321,7 +320,7 @@ int ParserATNSimulator::execATNWithFullContext(dfa::DFA *dfa, dfa::DFAState *D,
ATNConfigSet *reach = nullptr; ATNConfigSet *reach = nullptr;
ATNConfigSet *previous = s0; ATNConfigSet *previous = s0;
input->seek(startIndex); input->seek(startIndex);
size_t t = input->LA(1); ssize_t t = input->LA(1);
int predictedAlt; int predictedAlt;
while (true) { while (true) {
reach = computeReachSet(previous, t, fullCtx); reach = computeReachSet(previous, t, fullCtx);
@ -378,7 +377,7 @@ int ParserATNSimulator::execATNWithFullContext(dfa::DFA *dfa, dfa::DFAState *D,
} }
previous = reach; previous = reach;
if (t != IntStream::_EOF) { if (t != EOF) {
input->consume(); input->consume();
t = input->LA(1); t = input->LA(1);
} }
@ -424,16 +423,12 @@ int ParserATNSimulator::execATNWithFullContext(dfa::DFA *dfa, dfa::DFAState *D,
return predictedAlt; return predictedAlt;
} }
atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, size_t t, bool fullCtx) { atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, ssize_t t, bool fullCtx) {
if (debug) { if (debug) {
std::wcout << L"in computeReachSet, starting closure: " << closure << std::endl; std::wcout << L"in computeReachSet, starting closure: " << closure << std::endl;
} }
if (mergeCache == nullptr) { ATNConfigSet *intermediate = new ATNConfigSet(fullCtx, std::shared_ptr<ConfigLookup>());
mergeCache = new misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*>();
}
ATNConfigSet *intermediate = new ATNConfigSet(fullCtx);
/* Configurations already in a rule stop state indicate reaching the end /* Configurations already in a rule stop state indicate reaching the end
* of the decision rule (local context) or end of the start rule (full * of the decision rule (local context) or end of the start rule (full
@ -456,7 +451,7 @@ atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, si
if (dynamic_cast<RuleStopState*>(c->state) != nullptr) { if (dynamic_cast<RuleStopState*>(c->state) != nullptr) {
assert(c->context->isEmpty()); assert(c->context->isEmpty());
if (fullCtx || t == IntStream::_EOF) { if (fullCtx || t == EOF) {
if (skippedStopStates.empty()) { if (skippedStopStates.empty()) {
skippedStopStates = std::vector<ATNConfig*>(); skippedStopStates = std::vector<ATNConfig*>();
} }
@ -472,7 +467,7 @@ atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, si
Transition *trans = c->state->transition(ti); Transition *trans = c->state->transition(ti);
ATNState *target = getReachableTarget(trans, (int)t); ATNState *target = getReachableTarget(trans, (int)t);
if (target != nullptr) { if (target != nullptr) {
intermediate->add(new ATNConfig(c, target), mergeCache); intermediate->add(new ATNConfig(c, target), &mergeCache);
} }
} }
} }
@ -508,15 +503,15 @@ atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, si
* operation on the intermediate set to compute its initial value. * operation on the intermediate set to compute its initial value.
*/ */
if (reach == nullptr) { if (reach == nullptr) {
reach = new ATNConfigSet(fullCtx); reach = new ATNConfigSet(fullCtx, std::shared_ptr<ConfigLookup>());
std::set<ATNConfig*> *closureBusy = new std::set<ATNConfig*>(); std::set<ATNConfig*> closureBusy;
for (auto c : *intermediate->configLookup) { for (auto c : *intermediate->configLookup) {
this->closure(c, reach, closureBusy, false, fullCtx); this->closure(c, reach, closureBusy, false, fullCtx);
} }
} }
if (t == IntStream::_EOF) { if (t == EOF) {
/* After consuming EOF no additional input is possible, so we are /* After consuming EOF no additional input is possible, so we are
* only interested in configurations which reached the end of the * only interested in configurations which reached the end of the
* decision rule (local context) or end of the start rule (full * decision rule (local context) or end of the start rule (full
@ -549,7 +544,7 @@ atn::ATNConfigSet *ParserATNSimulator::computeReachSet(ATNConfigSet *closure, si
assert(!skippedStopStates.empty()); assert(!skippedStopStates.empty());
for (auto c : skippedStopStates) { for (auto c : skippedStopStates) {
reach->add(c, mergeCache); reach->add(c, &mergeCache);
} }
} }
@ -564,11 +559,11 @@ atn::ATNConfigSet *ParserATNSimulator::removeAllConfigsNotInRuleStopState(ATNCon
return configs; return configs;
} }
ATNConfigSet *result = new ATNConfigSet(configs->fullCtx); ATNConfigSet *result = new ATNConfigSet(configs->fullCtx, std::shared_ptr<ConfigLookup>());
for (auto config : *configs->configLookup) { for (auto config : *configs->configLookup) {
if (dynamic_cast<RuleStopState*>(config->state) != nullptr) { if (dynamic_cast<RuleStopState*>(config->state) != nullptr) {
result->add(config, mergeCache); result->add(config, &mergeCache);
continue; continue;
} }
@ -576,7 +571,7 @@ atn::ATNConfigSet *ParserATNSimulator::removeAllConfigsNotInRuleStopState(ATNCon
misc::IntervalSet nextTokens = atn.nextTokens(config->state); misc::IntervalSet nextTokens = atn.nextTokens(config->state);
if (nextTokens.contains(Token::EPSILON)) { if (nextTokens.contains(Token::EPSILON)) {
ATNState *endOfRuleState = atn.ruleToStopState[(size_t)config->state->ruleIndex]; ATNState *endOfRuleState = atn.ruleToStopState[(size_t)config->state->ruleIndex];
result->add(new ATNConfig(config, endOfRuleState), mergeCache); result->add(new ATNConfig(config, endOfRuleState), &mergeCache);
} }
} }
} }
@ -586,13 +581,13 @@ atn::ATNConfigSet *ParserATNSimulator::removeAllConfigsNotInRuleStopState(ATNCon
atn::ATNConfigSet *ParserATNSimulator::computeStartState(ATNState *p, RuleContext *ctx, bool fullCtx) { atn::ATNConfigSet *ParserATNSimulator::computeStartState(ATNState *p, RuleContext *ctx, bool fullCtx) {
// always at least the implicit call to start rule // always at least the implicit call to start rule
PredictionContext *initialContext = PredictionContext::fromRuleContext(atn, ctx); PredictionContextRef initialContext = PredictionContext::fromRuleContext(atn, ctx);
ATNConfigSet *configs = new ATNConfigSet(fullCtx); ATNConfigSet *configs = new ATNConfigSet(fullCtx, std::shared_ptr<ConfigLookup>());
for (size_t i = 0; i < p->getNumberOfTransitions(); i++) { for (size_t i = 0; i < p->getNumberOfTransitions(); i++) {
ATNState *target = p->transition(i)->target; ATNState *target = p->transition(i)->target;
ATNConfig *c = new ATNConfig(target, (int)i + 1, initialContext); ATNConfig *c = new ATNConfig(target, (int)i + 1, initialContext);
std::set<ATNConfig*> *closureBusy = new std::set<ATNConfig*>(); std::set<ATNConfig*> closureBusy;
closure(c, configs, closureBusy, true, fullCtx); closure(c, configs, closureBusy, true, fullCtx);
} }
@ -607,9 +602,9 @@ atn::ATNState *ParserATNSimulator::getReachableTarget(Transition *trans, int tty
return nullptr; return nullptr;
} }
//
// Note that caller must memory manage the returned value from this function // Note that caller must memory manage the returned value from this function
std::vector<SemanticContext*> ParserATNSimulator::getPredsForAmbigAlts(BitSet *ambigAlts, ATNConfigSet *configs, size_t nalts) { std::vector<SemanticContextRef> ParserATNSimulator::getPredsForAmbigAlts(BitSet *ambigAlts,
ATNConfigSet *configs, size_t nalts) {
// REACH=[1|1|[]|0:0, 1|2|[]|0:1] // REACH=[1|1|[]|0:0, 1|2|[]|0:1]
/* altToPred starts as an array of all null contexts. The entry at index i /* altToPred starts as an array of all null contexts. The entry at index i
* corresponds to alternative i. altToPred[i] may have one of three values: * corresponds to alternative i. altToPred[i] may have one of three values:
@ -622,12 +617,13 @@ std::vector<SemanticContext*> ParserATNSimulator::getPredsForAmbigAlts(BitSet *a
* *
* From this, it is clear that NONE||anything==NONE. * From this, it is clear that NONE||anything==NONE.
*/ */
//SemanticContext *altToPred = new SemanticContext[nalts + 1]; std::vector<SemanticContextRef> altToPred;
std::vector<SemanticContext*> altToPred;// = new SemanticContext[nalts + 1];
for (auto c : *configs->configLookup) { for (auto c : *configs->configLookup) {
if (ambigAlts->data.test((size_t)c->alt)) { if (ambigAlts->data.test((size_t)c->alt)) {
altToPred[(size_t)c->alt] = dynamic_cast<SemanticContext*>( (new SemanticContext::OR(altToPred[(size_t)c->alt], c->semanticContext))); if (altToPred.size() <= (size_t)c->alt)
altToPred.resize((size_t)c->alt + 1);
altToPred[(size_t)c->alt] = std::make_shared<SemanticContext::OR>(altToPred[(size_t)c->alt], c->semanticContext);
} }
} }
@ -640,26 +636,22 @@ std::vector<SemanticContext*> ParserATNSimulator::getPredsForAmbigAlts(BitSet *a
} }
} }
// // Optimize away p||p and p&&p TODO: optimize() was a no-op
// for (int i = 0; i < altToPred.length; i++) {
// altToPred[i] = altToPred[i].optimize();
// }
// nonambig alts are null in altToPred // nonambig alts are null in altToPred
if (nPredAlts == 0) { if (nPredAlts == 0) {
altToPred.clear();// = nullptr; altToPred.clear();
} }
if (debug) { if (debug) {
std::wcout << L"getPredsForAmbigAlts result "; /* TODO << Arrays->toString(altToPred) << std::endl; */ std::wcout << L"getPredsForAmbigAlts result " << Arrays::toString(altToPred) << std::endl;
} }
return altToPred; return altToPred;
} }
std::vector<dfa::DFAState::PredPrediction *> ParserATNSimulator::getPredicatePredictions(BitSet *ambigAlts, std::vector<SemanticContext*> altToPred) { std::vector<dfa::DFAState::PredPrediction *> ParserATNSimulator::getPredicatePredictions(BitSet *ambigAlts,
std::vector<dfa::DFAState::PredPrediction*> pairs = std::vector<dfa::DFAState::PredPrediction*>(); std::vector<SemanticContextRef> altToPred) {
std::vector<dfa::DFAState::PredPrediction*> pairs;
bool containsPredicate = false; bool containsPredicate = false;
for (size_t i = 1; i < altToPred.size(); i++) { for (size_t i = 1; i < altToPred.size(); i++) {
SemanticContext *pred = altToPred[i]; SemanticContextRef pred = altToPred[i];
// unpredicted is indicated by SemanticContext.NONE // unpredicted is indicated by SemanticContext.NONE
assert(pred != nullptr); assert(pred != nullptr);
@ -722,14 +714,14 @@ BitSet *ParserATNSimulator::evalSemanticContext(std::vector<dfa::DFAState::PredP
return predictions; return predictions;
} }
void ParserATNSimulator::closure(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx) { void ParserATNSimulator::closure(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy, bool collectPredicates, bool fullCtx) {
const int initialDepth = 0; const int initialDepth = 0;
closureCheckingStopState(config, configs, closureBusy, collectPredicates, fullCtx, initialDepth); closureCheckingStopState(config, configs, closureBusy, collectPredicates, fullCtx, initialDepth);
assert(!fullCtx || !configs->dipsIntoOuterContext); assert(!fullCtx || !configs->dipsIntoOuterContext);
} }
void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx, int depth) { void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy, bool collectPredicates, bool fullCtx, int depth) {
if (debug) { if (debug) {
std::wcout << L"closure(" << config->toString(true) << L")" << std::endl; std::wcout << L"closure(" << config->toString(true) << L")" << std::endl;
} }
@ -741,7 +733,7 @@ void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSe
for (size_t i = 0; i < config->context->size(); i++) { for (size_t i = 0; i < config->context->size(); i++) {
if (config->context->getReturnState(i) == PredictionContext::EMPTY_RETURN_STATE) { if (config->context->getReturnState(i) == PredictionContext::EMPTY_RETURN_STATE) {
if (fullCtx) { if (fullCtx) {
configs->add(new ATNConfig(config, config->state, dynamic_cast<PredictionContext*>(PredictionContext::EMPTY)), mergeCache); configs->add(new ATNConfig(config, config->state, PredictionContext::EMPTY), &mergeCache);
continue; continue;
} else { } else {
// we have no context info, just chase follow links (if greedy) // we have no context info, just chase follow links (if greedy)
@ -753,8 +745,8 @@ void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSe
continue; continue;
} }
ATNState *returnState = atn.states[(size_t)config->context->getReturnState(i)]; ATNState *returnState = atn.states[(size_t)config->context->getReturnState(i)];
PredictionContext *newContext = config->context->getParent(i); // "pop" return state std::weak_ptr<PredictionContext> newContext = config->context->getParent(i); // "pop" return state
ATNConfig *c = new ATNConfig(returnState, config->alt, newContext, config->semanticContext); ATNConfig *c = new ATNConfig(returnState, config->alt, newContext.lock(), config->semanticContext);
// While we have context to pop back from, we may have // While we have context to pop back from, we may have
// gotten that context AFTER having falling off a rule. // gotten that context AFTER having falling off a rule.
// Make sure we track that we are now out of context. // Make sure we track that we are now out of context.
@ -766,7 +758,7 @@ void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSe
return; return;
} else if (fullCtx) { } else if (fullCtx) {
// reached end of start rule // reached end of start rule
configs->add(config, mergeCache); configs->add(config, &mergeCache);
return; return;
} else { } else {
// else if we have no context info, just chase follow links (if greedy) // else if we have no context info, just chase follow links (if greedy)
@ -779,12 +771,11 @@ void ParserATNSimulator::closureCheckingStopState(ATNConfig *config, ATNConfigSe
closure_(config, configs, closureBusy, collectPredicates, fullCtx, depth); closure_(config, configs, closureBusy, collectPredicates, fullCtx, depth);
} }
void ParserATNSimulator::closure_(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx, int depth) { void ParserATNSimulator::closure_(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy, bool collectPredicates, bool fullCtx, int depth) {
ATNState *p = config->state; ATNState *p = config->state;
// optimization // optimization
if (!p->onlyHasEpsilonTransitions()) { if (!p->onlyHasEpsilonTransitions()) {
configs->add(config, mergeCache); configs->add(config, &mergeCache);
// if ( debug ) System.out.println("added config "+configs);
} }
for (size_t i = 0; i < p->getNumberOfTransitions(); i++) { for (size_t i = 0; i < p->getNumberOfTransitions(); i++) {
@ -802,13 +793,14 @@ void ParserATNSimulator::closure_(ATNConfig *config, ATNConfigSet *configs, std:
// come in handy and we avoid evaluating context dependent // come in handy and we avoid evaluating context dependent
// preds if this is > 0. // preds if this is > 0.
if (!closureBusy->insert(c).second) { if (closureBusy.count(c) > 0) {
// avoid infinite recursion for right-recursive rules // avoid infinite recursion for right-recursive rules
continue; continue;
} }
closureBusy.insert(c);
c->reachesIntoOuterContext++; c->reachesIntoOuterContext++;
configs->dipsIntoOuterContext = true; // TODO: can remove? only care when we add to set per middle of this method configs->dipsIntoOuterContext = true; // TO_DO: can remove? only care when we add to set per middle of this method
assert(newDepth > INT_MIN); assert(newDepth > INT_MIN);
newDepth--; newDepth--;
@ -874,6 +866,8 @@ atn::ATNConfig *ParserATNSimulator::precedenceTransition(ATNConfig *config, Prec
ATNConfig *c = nullptr; ATNConfig *c = nullptr;
if (collectPredicates && inContext) { if (collectPredicates && inContext) {
std::shared_ptr<SemanticContext::PrecedencePredicate> predicate = pt->getPredicate();
if (fullCtx) { if (fullCtx) {
// In full context mode, we can evaluate predicates on-the-fly // In full context mode, we can evaluate predicates on-the-fly
// during closure, which dramatically reduces the size of // during closure, which dramatically reduces the size of
@ -881,14 +875,14 @@ atn::ATNConfig *ParserATNSimulator::precedenceTransition(ATNConfig *config, Prec
// later during conflict resolution. // later during conflict resolution.
size_t currentPosition = _input->index(); size_t currentPosition = _input->index();
_input->seek((size_t)_startIndex); _input->seek((size_t)_startIndex);
bool predSucceeds = pt->getPredicate()->eval(parser, _outerContext); bool predSucceeds = predicate->eval(parser, _outerContext);
_input->seek(currentPosition); _input->seek(currentPosition);
if (predSucceeds) { if (predSucceeds) {
c = new ATNConfig(config, pt->target); // no pred context c = new ATNConfig(config, pt->target); // no pred context
} }
} else { } else {
SemanticContext *newSemCtx = new SemanticContext::AND(config->semanticContext, pt->getPredicate()); std::shared_ptr<SemanticContext::AND> newSemCtx = std::make_shared<SemanticContext::AND>(config->semanticContext, predicate);
c = new ATNConfig(config, pt->target, newSemCtx); c = new ATNConfig(config, pt->target, std::dynamic_pointer_cast<SemanticContext>(newSemCtx));
} }
} else { } else {
c = new ATNConfig(config, pt->target); c = new ATNConfig(config, pt->target);
@ -910,6 +904,7 @@ atn::ATNConfig *ParserATNSimulator::predTransition(ATNConfig *config, PredicateT
ATNConfig *c = nullptr; ATNConfig *c = nullptr;
if (collectPredicates && (!pt->isCtxDependent || (pt->isCtxDependent && inContext))) { if (collectPredicates && (!pt->isCtxDependent || (pt->isCtxDependent && inContext))) {
std::shared_ptr<SemanticContext::Predicate> predicate = pt->getPredicate();
if (fullCtx) { if (fullCtx) {
// In full context mode, we can evaluate predicates on-the-fly // In full context mode, we can evaluate predicates on-the-fly
// during closure, which dramatically reduces the size of // during closure, which dramatically reduces the size of
@ -917,14 +912,14 @@ atn::ATNConfig *ParserATNSimulator::predTransition(ATNConfig *config, PredicateT
// later during conflict resolution. // later during conflict resolution.
size_t currentPosition = _input->index(); size_t currentPosition = _input->index();
_input->seek((size_t)_startIndex); _input->seek((size_t)_startIndex);
bool predSucceeds = pt->getPredicate()->eval(parser, _outerContext); bool predSucceeds = predicate->eval(parser, _outerContext);
_input->seek(currentPosition); _input->seek(currentPosition);
if (predSucceeds) { if (predSucceeds) {
c = new ATNConfig(config, pt->target); // no pred context c = new ATNConfig(config, pt->target); // no pred context
} }
} else { } else {
SemanticContext *newSemCtx = dynamic_cast<SemanticContext*>(new SemanticContext::AND(config->semanticContext, pt->getPredicate())); std::shared_ptr<SemanticContext::AND> newSemCtx = std::make_shared<SemanticContext::AND>(config->semanticContext, predicate);
c = new ATNConfig(config, pt->target, newSemCtx); c = new ATNConfig(config, pt->target, std::dynamic_pointer_cast<SemanticContext>(newSemCtx));
} }
} else { } else {
c = new ATNConfig(config, pt->target); c = new ATNConfig(config, pt->target);
@ -942,7 +937,7 @@ atn::ATNConfig *ParserATNSimulator::ruleTransition(ATNConfig *config, RuleTransi
} }
atn::ATNState *returnState = t->followState; atn::ATNState *returnState = t->followState;
PredictionContext *newContext = SingletonPredictionContext::create(config->context, returnState->stateNumber); PredictionContextRef newContext = SingletonPredictionContext::create(config->context, returnState->stateNumber);
return new atn::ATNConfig(config, t->target, newContext); return new atn::ATNConfig(config, t->target, newContext);
} }
@ -961,18 +956,17 @@ BitSet ParserATNSimulator::getConflictingAltsOrUniqueAlt(ATNConfigSet *configs)
return conflictingAlts; return conflictingAlts;
} }
std::wstring ParserATNSimulator::getTokenName(size_t t) { std::wstring ParserATNSimulator::getTokenName(ssize_t t) {
if (t == Token::_EOF) { if (t == EOF) {
return L"EOF"; return L"EOF";
} }
if (parser != nullptr) { if (parser != nullptr) {
std::vector<std::wstring> tokensNames = parser->getTokenNames(); std::vector<std::wstring> tokensNames = parser->getTokenNames();
if (t >= tokensNames.size()) { if (t >= (ssize_t)tokensNames.size()) {
std::wcerr << t << L" type out of range: " << Arrays::listToString(tokensNames, L", "); std::wcerr << t << L" type out of range: " << Arrays::listToString(tokensNames, L", ");
// TODO std::wcerr << Arrays::toString(((CommonTokenStream*)parser->getInputStream())->getTokens());
// std::wcerr << ((CommonTokenStream*)parser->getInputStream())->getTokens();
} else { } else {
return tokensNames[t] + L"<" + std::to_wstring(t) + L">"; return tokensNames[(size_t)t] + L"<" + std::to_wstring(t) + L">";
} }
} }
return StringConverterHelper::toString(t); return StringConverterHelper::toString(t);
@ -990,7 +984,7 @@ void ParserATNSimulator::dumpDeadEndConfigs(NoViableAltException *nvae) {
Transition *t = c->state->transition(0); Transition *t = c->state->transition(0);
if (dynamic_cast<AtomTransition*>(t) != nullptr) { if (dynamic_cast<AtomTransition*>(t) != nullptr) {
AtomTransition *at = static_cast<AtomTransition*>(t); AtomTransition *at = static_cast<AtomTransition*>(t);
trans = L"Atom " + getTokenName((size_t)at->_label); trans = L"Atom " + getTokenName(at->_label);
} else if (dynamic_cast<SetTransition*>(t) != nullptr) { } else if (dynamic_cast<SetTransition*>(t) != nullptr) {
SetTransition *st = static_cast<SetTransition*>(t); SetTransition *st = static_cast<SetTransition*>(t);
bool is_not = dynamic_cast<NotSetTransition*>(st) != nullptr; bool is_not = dynamic_cast<NotSetTransition*>(st) != nullptr;
@ -1020,7 +1014,7 @@ int ParserATNSimulator::getUniqueAlt(ATNConfigSet *configs) {
return alt; return alt;
} }
dfa::DFAState *ParserATNSimulator::addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from, size_t t, dfa::DFAState *to) { dfa::DFAState *ParserATNSimulator::addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from, ssize_t t, dfa::DFAState *to) {
if (debug) { if (debug) {
std::wcout << L"EDGE " << from << L" -> " << to << L" upon " << getTokenName(t) << std::endl; std::wcout << L"EDGE " << from << L" -> " << to << L" upon " << getTokenName(t) << std::endl;
} }
@ -1030,7 +1024,7 @@ dfa::DFAState *ParserATNSimulator::addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from
} }
to = addDFAState(dfa, to); // used existing if possible not incoming to = addDFAState(dfa, to); // used existing if possible not incoming
if (from == nullptr || t > (size_t)atn.maxTokenType) { if (from == nullptr || t > atn.maxTokenType) {
return to; return to;
} }
@ -1041,7 +1035,7 @@ dfa::DFAState *ParserATNSimulator::addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from
from->edges = std::vector<dfa::DFAState*>(); from->edges = std::vector<dfa::DFAState*>();
} }
from->edges[t + 1] = to; // connect from->edges[(size_t)(t + 1)] = to; // connect
} }
if (debug) { if (debug) {

View File

@ -34,6 +34,8 @@
#include "PredictionMode.h" #include "PredictionMode.h"
#include "DFAState.h" #include "DFAState.h"
#include "ATNSimulator.h" #include "ATNSimulator.h"
#include "PredictionContext.h"
#include "SemanticContext.h"
namespace org { namespace org {
namespace antlr { namespace antlr {
@ -238,6 +240,7 @@ namespace atn {
/// passes over the input. /// passes over the input.
/// ///
/// </summary> /// </summary>
class ParserATNSimulator : public ATNSimulator { class ParserATNSimulator : public ATNSimulator {
public: public:
static const bool debug = false; static const bool debug = false;
@ -260,7 +263,7 @@ namespace atn {
/// <summary> /// <summary>
/// Each prediction operation uses a cache for merge of prediction contexts. /// Each prediction operation uses a cache for merge of prediction contexts.
/// Don't keep around as it wastes huge amounts of memory. DoubleKeyMap /// Don't keep around as it wastes huge amounts of memory. The merge cache
/// isn't synchronized but we're ok since two threads shouldn't reuse same /// isn't synchronized but we're ok since two threads shouldn't reuse same
/// parser/atnsim object because it can only handle one input at a time. /// parser/atnsim object because it can only handle one input at a time.
/// This maps graphs a and b to merged result c. (a,b)->c. We can avoid /// This maps graphs a and b to merged result c. (a,b)->c. We can avoid
@ -268,7 +271,7 @@ namespace atn {
/// also be examined during cache lookup. /// also be examined during cache lookup.
/// </summary> /// </summary>
protected: protected:
misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache; PredictionContextMergeCache mergeCache;
// LAME globals to avoid parameters!!!!! I need these down deep in predTransition // LAME globals to avoid parameters!!!!! I need these down deep in predTransition
TokenStream *_input; TokenStream *_input;
@ -278,9 +281,11 @@ namespace atn {
/// <summary> /// <summary>
/// Testing only! </summary> /// Testing only! </summary>
public: public:
ParserATNSimulator(const ATN &atn, const std::vector<dfa::DFA *>& decisionToDFA, PredictionContextCache *sharedContextCache); ParserATNSimulator(const ATN &atn, const std::vector<dfa::DFA *>& decisionToDFA,
std::shared_ptr<PredictionContextCache> sharedContextCache);
ParserATNSimulator(Parser *parser, const ATN &atn, const std::vector<dfa::DFA *>& decisionToDFA, PredictionContextCache *sharedContextCache); ParserATNSimulator(Parser *parser, const ATN &atn, const std::vector<dfa::DFA *> &decisionToDFA,
std::shared_ptr<PredictionContextCache> sharedContextCache);
virtual void reset() override; virtual void reset() override;
@ -330,7 +335,7 @@ namespace atn {
/// <returns> The existing target DFA state for the given input symbol /// <returns> The existing target DFA state for the given input symbol
/// {@code t}, or {@code null} if the target state for this edge is not /// {@code t}, or {@code null} if the target state for this edge is not
/// already cached </returns> /// already cached </returns>
virtual dfa::DFAState *getExistingTargetState(dfa::DFAState *previousD, size_t t); virtual dfa::DFAState* getExistingTargetState(dfa::DFAState *previousD, ssize_t t);
/// <summary> /// <summary>
/// Compute a target state for an edge in the DFA, and attempt to add the /// Compute a target state for an edge in the DFA, and attempt to add the
@ -343,14 +348,14 @@ namespace atn {
/// <returns> The computed target DFA state for the given input symbol /// <returns> The computed target DFA state for the given input symbol
/// {@code t}. If {@code t} does not lead to a valid DFA state, this method /// {@code t}. If {@code t} does not lead to a valid DFA state, this method
/// returns <seealso cref="#ERROR"/>. </returns> /// returns <seealso cref="#ERROR"/>. </returns>
virtual dfa::DFAState *computeTargetState(dfa::DFA *dfa, dfa::DFAState *previousD, size_t t); virtual dfa::DFAState *computeTargetState(dfa::DFA *dfa, dfa::DFAState *previousD, ssize_t t);
virtual void predicateDFAState(dfa::DFAState *dfaState, DecisionState *decisionState); virtual void predicateDFAState(dfa::DFAState *dfaState, DecisionState *decisionState);
// comes back with reach.uniqueAlt set to a valid alt // comes back with reach.uniqueAlt set to a valid alt
virtual int execATNWithFullContext(dfa::DFA *dfa, dfa::DFAState *D, ATNConfigSet *s0, TokenStream *input, size_t startIndex, ParserRuleContext *outerContext); // how far we got before failing over virtual int execATNWithFullContext(dfa::DFA *dfa, dfa::DFAState *D, ATNConfigSet *s0, TokenStream *input, size_t startIndex, ParserRuleContext *outerContext); // how far we got before failing over
virtual ATNConfigSet *computeReachSet(ATNConfigSet *closure, size_t t, bool fullCtx); virtual ATNConfigSet *computeReachSet(ATNConfigSet *closure, ssize_t t, bool fullCtx);
/// <summary> /// <summary>
/// Return a configuration set containing only the configurations from /// Return a configuration set containing only the configurations from
@ -377,9 +382,11 @@ namespace atn {
virtual ATNState *getReachableTarget(Transition *trans, int ttype); virtual ATNState *getReachableTarget(Transition *trans, int ttype);
virtual std::vector<SemanticContext*> getPredsForAmbigAlts(antlrcpp::BitSet *ambigAlts, ATNConfigSet *configs, size_t nalts); virtual std::vector<SemanticContextRef> getPredsForAmbigAlts(antlrcpp::BitSet *ambigAlts,
ATNConfigSet *configs, size_t nalts);
virtual std::vector<dfa::DFAState::PredPrediction*> getPredicatePredictions(antlrcpp::BitSet *ambigAlts, std::vector<SemanticContext*> altToPred); virtual std::vector<dfa::DFAState::PredPrediction*> getPredicatePredictions(antlrcpp::BitSet *ambigAlts,
std::vector<SemanticContextRef> altToPred);
virtual int getAltThatFinishedDecisionEntryRule(ATNConfigSet *configs); virtual int getAltThatFinishedDecisionEntryRule(ATNConfigSet *configs);
@ -393,27 +400,28 @@ namespace atn {
virtual antlrcpp::BitSet *evalSemanticContext(std::vector<dfa::DFAState::PredPrediction*> predPredictions, ParserRuleContext *outerContext, bool complete); virtual antlrcpp::BitSet *evalSemanticContext(std::vector<dfa::DFAState::PredPrediction*> predPredictions, ParserRuleContext *outerContext, bool complete);
/* TODO: If we are doing predicates, there is no point in pursuing /* TO_DO: If we are doing predicates, there is no point in pursuing
closure operations if we reach a DFA state that uniquely predicts closure operations if we reach a DFA state that uniquely predicts
alternative. We will not be caching that DFA state and it is a alternative. We will not be caching that DFA state and it is a
waste to pursue the closure. Might have to advance when we do waste to pursue the closure. Might have to advance when we do
ambig detection thought :( ambig detection thought :(
*/ */
virtual void closure(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx); virtual void closure(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy,
bool collectPredicates, bool fullCtx);
virtual void closureCheckingStopState(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx, int depth); virtual void closureCheckingStopState(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy,
bool collectPredicates, bool fullCtx, int depth);
/// <summary> /// Do the actual work of walking epsilon edges.
/// Do the actual work of walking epsilon edges </summary> virtual void closure_(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> &closureBusy,
virtual void closure_(ATNConfig *config, ATNConfigSet *configs, std::set<ATNConfig*> *closureBusy, bool collectPredicates, bool fullCtx, int depth); bool collectPredicates, bool fullCtx, int depth);
public: public:
virtual std::wstring getRuleName(size_t index); virtual std::wstring getRuleName(size_t index);
protected: protected:
virtual ATNConfig *getEpsilonTarget(ATNConfig *config, Transition *t, bool collectPredicates, bool inContext, bool fullCtx); virtual ATNConfig *getEpsilonTarget(ATNConfig *config, Transition *t, bool collectPredicates, bool inContext, bool fullCtx);
virtual ATNConfig *actionTransition(ATNConfig *config, ActionTransition *t); virtual ATNConfig *actionTransition(ATNConfig *config, ActionTransition *t);
public: public:
@ -466,7 +474,7 @@ namespace atn {
virtual antlrcpp::BitSet getConflictingAltsOrUniqueAlt(ATNConfigSet *configs); virtual antlrcpp::BitSet getConflictingAltsOrUniqueAlt(ATNConfigSet *configs);
public: public:
virtual std::wstring getTokenName(size_t t); virtual std::wstring getTokenName(ssize_t t);
virtual std::wstring getLookaheadName(TokenStream *input); virtual std::wstring getLookaheadName(TokenStream *input);
@ -501,7 +509,7 @@ namespace atn {
/// <returns> If {@code to} is {@code null}, this method returns {@code null}; /// <returns> If {@code to} is {@code null}, this method returns {@code null};
/// otherwise this method returns the result of calling <seealso cref="#addDFAState"/> /// otherwise this method returns the result of calling <seealso cref="#addDFAState"/>
/// on {@code to} </returns> /// on {@code to} </returns>
virtual dfa::DFAState *addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from, size_t t, dfa::DFAState *to); virtual dfa::DFAState *addDFAEdge(dfa::DFA *dfa, dfa::DFAState *from, ssize_t t, dfa::DFAState *to);
/// <summary> /// <summary>
/// Add state {@code D} to the DFA if it is not already present, and return /// Add state {@code D} to the DFA if it is not already present, and return

View File

@ -48,8 +48,8 @@ bool PrecedencePredicateTransition::matches(int symbol, int minVocabSymbol, int
return false; return false;
} }
org::antlr::v4::runtime::atn::SemanticContext::PrecedencePredicate *PrecedencePredicateTransition::getPredicate() const { std::shared_ptr<SemanticContext::PrecedencePredicate> PrecedencePredicateTransition::getPredicate() const {
return new SemanticContext::PrecedencePredicate(precedence); return std::make_shared<SemanticContext::PrecedencePredicate>(precedence);
} }
std::wstring PrecedencePredicateTransition::toString() const { std::wstring PrecedencePredicateTransition::toString() const {

View File

@ -47,13 +47,9 @@ namespace atn {
PrecedencePredicateTransition(ATNState *target, int precedence); PrecedencePredicateTransition(ATNState *target, int precedence);
virtual int getSerializationType() const override; virtual int getSerializationType() const override;
virtual bool isEpsilon() const override; virtual bool isEpsilon() const override;
virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const override; virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const override;
std::shared_ptr<SemanticContext::PrecedencePredicate> getPredicate() const;
SemanticContext::PrecedencePredicate *getPredicate() const;
virtual std::wstring toString() const; virtual std::wstring toString() const;
}; };

View File

@ -49,9 +49,8 @@ bool PredicateTransition::matches(int symbol, int minVocabSymbol, int maxVocabSy
return false; return false;
} }
SemanticContext::Predicate *PredicateTransition::getPredicate() const { std::shared_ptr<SemanticContext::Predicate> PredicateTransition::getPredicate() const {
// TODO: who is responsible for managing this memory? return std::make_shared<SemanticContext::Predicate>(ruleIndex, predIndex, isCtxDependent);
return new SemanticContext::Predicate(ruleIndex, predIndex, isCtxDependent);
} }
std::wstring PredicateTransition::toString() const { std::wstring PredicateTransition::toString() const {

View File

@ -40,13 +40,11 @@ namespace v4 {
namespace runtime { namespace runtime {
namespace atn { namespace atn {
/// <summary> /// TO_DO: this is old comment:
/// TODO: this is old comment:
/// A tree of semantic predicates from the grammar AST if label==SEMPRED. /// A tree of semantic predicates from the grammar AST if label==SEMPRED.
/// In the ATN, labels will always be exactly one predicate, but the DFA /// In the ATN, labels will always be exactly one predicate, but the DFA
/// may have to combine a bunch of them as it collects predicates from /// may have to combine a bunch of them as it collects predicates from
/// multiple ATN configurations into a single DFA state. /// multiple ATN configurations into a single DFA state.
/// </summary>
class PredicateTransition final : public AbstractPredicateTransition { class PredicateTransition final : public AbstractPredicateTransition {
public: public:
const int ruleIndex; const int ruleIndex;
@ -60,7 +58,7 @@ namespace atn {
virtual bool isEpsilon() const override; virtual bool isEpsilon() const override;
virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const override; virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const override;
SemanticContext::Predicate *getPredicate() const; std::shared_ptr<SemanticContext::Predicate> getPredicate() const;
virtual std::wstring toString() const; virtual std::wstring toString() const;

View File

@ -35,9 +35,8 @@
#include "RuleContext.h" #include "RuleContext.h"
#include "RuleTransition.h" #include "RuleTransition.h"
#include "stringconverter.h" #include "stringconverter.h"
#include "PredictionContextCache.h"
#include "DoubleKeyMap.h"
#include "Arrays.h" #include "Arrays.h"
#include "CPPUtils.h"
#include "PredictionContext.h" #include "PredictionContext.h"
@ -47,14 +46,14 @@ using namespace org::antlr::v4::runtime::atn;
using namespace antlrcpp; using namespace antlrcpp;
int PredictionContext::globalNodeCount = 0; int PredictionContext::globalNodeCount = 0;
EmptyPredictionContext * PredictionContext::EMPTY; const std::shared_ptr<EmptyPredictionContext> PredictionContext::EMPTY;
const int PredictionContext::EMPTY_RETURN_STATE; const int PredictionContext::EMPTY_RETURN_STATE;
const int PredictionContext::INITIAL_HASH; const int PredictionContext::INITIAL_HASH;
PredictionContext::PredictionContext(size_t cachedHashCode) : id(globalNodeCount++), cachedHashCode(cachedHashCode) { PredictionContext::PredictionContext(size_t cachedHashCode) : id(globalNodeCount++), cachedHashCode(cachedHashCode) {
} }
PredictionContext *PredictionContext::fromRuleContext(const ATN &atn, RuleContext *outerContext) { PredictionContextRef PredictionContext::fromRuleContext(const ATN &atn, RuleContext *outerContext) {
if (outerContext == nullptr) { if (outerContext == nullptr) {
outerContext = (RuleContext*)RuleContext::EMPTY; outerContext = (RuleContext*)RuleContext::EMPTY;
} }
@ -66,11 +65,10 @@ PredictionContext *PredictionContext::fromRuleContext(const ATN &atn, RuleContex
} }
// If we have a parent, convert it to a PredictionContext graph // If we have a parent, convert it to a PredictionContext graph
PredictionContext *parent = EMPTY; PredictionContextRef parent = PredictionContext::fromRuleContext(atn, outerContext->parent);
parent = PredictionContext::fromRuleContext(atn, outerContext->parent);
ATNState *state = atn.states[(size_t)outerContext->invokingState]; ATNState *state = atn.states[(size_t)outerContext->invokingState];
RuleTransition *transition = (RuleTransition *)state->transition(0);//static_cast<RuleTransition*>(state->transition(0)); RuleTransition *transition = (RuleTransition *)state->transition(0);
return SingletonPredictionContext::create(parent, transition->followState->stateNumber); return SingletonPredictionContext::create(parent, transition->followState->stateNumber);
} }
@ -79,7 +77,7 @@ bool PredictionContext::operator != (const PredictionContext &o) const {
}; };
bool PredictionContext::isEmpty() const { bool PredictionContext::isEmpty() const {
return this == EMPTY; return this == EMPTY.get();
} }
bool PredictionContext::hasEmptyPath() const { bool PredictionContext::hasEmptyPath() const {
@ -96,19 +94,20 @@ size_t PredictionContext::calculateEmptyHashCode() {
return hash; return hash;
} }
size_t PredictionContext::calculateHashCode(PredictionContext *parent, int returnState) { size_t PredictionContext::calculateHashCode(std::weak_ptr<PredictionContext> parent, int returnState) {
size_t hash = MurmurHash::initialize(INITIAL_HASH); size_t hash = MurmurHash::initialize(INITIAL_HASH);
hash = MurmurHash::update(hash, (size_t)parent); hash = MurmurHash::update(hash, (size_t)parent.lock().get());
hash = MurmurHash::update(hash, (size_t)returnState); hash = MurmurHash::update(hash, (size_t)returnState);
hash = MurmurHash::finish(hash, 2); hash = MurmurHash::finish(hash, 2);
return hash; return hash;
} }
size_t PredictionContext::calculateHashCode(const std::vector<PredictionContext*> &parents, const std::vector<int> &returnStates) { size_t PredictionContext::calculateHashCode(const std::vector<std::weak_ptr<PredictionContext>> &parents,
const std::vector<int> &returnStates) {
size_t hash = MurmurHash::initialize(INITIAL_HASH); size_t hash = MurmurHash::initialize(INITIAL_HASH);
for (auto parent : parents) { for (auto parent : parents) {
hash = MurmurHash::update(hash, (size_t)parent); hash = MurmurHash::update(hash, (size_t)parent.lock().get());
} }
for (auto returnState : returnStates) { for (auto returnState : returnStates) {
@ -118,184 +117,198 @@ size_t PredictionContext::calculateHashCode(const std::vector<PredictionContext*
return MurmurHash::finish(hash, parents.size() + returnStates.size()); return MurmurHash::finish(hash, parents.size() + returnStates.size());
} }
PredictionContext *PredictionContext::merge(PredictionContext *a, PredictionContext *b, PredictionContextRef PredictionContext::merge(PredictionContextRef a,
bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache) { PredictionContextRef b, bool rootIsWildcard, PredictionContextMergeCache *mergeCache) {
assert(a != nullptr && b != nullptr);
assert(a && b);
// share same graph if both same // share same graph if both same
if (a == b) { if (a == b) {
return a; return a;
} }
if (dynamic_cast<SingletonPredictionContext*>(a) != nullptr && dynamic_cast<SingletonPredictionContext*>(b) != nullptr) { if (is<SingletonPredictionContext>(a) && is<SingletonPredictionContext>(b)) {
return mergeSingletons(static_cast<SingletonPredictionContext*>(a), static_cast<SingletonPredictionContext*>(b), rootIsWildcard, mergeCache); return mergeSingletons(std::dynamic_pointer_cast<SingletonPredictionContext>(a),
std::dynamic_pointer_cast<SingletonPredictionContext>(b), rootIsWildcard, mergeCache);
} }
// At least one of a or b is array // At least one of a or b is array
// If one is $ and rootIsWildcard, return $ as * wildcard // If one is $ and rootIsWildcard, return $ as * wildcard
if (rootIsWildcard) { if (rootIsWildcard) {
if (dynamic_cast<EmptyPredictionContext*>(a) != nullptr) { if (is<EmptyPredictionContext>(a)) {
return a; return a;
} }
if (dynamic_cast<EmptyPredictionContext*>(b) != nullptr) { if (is<EmptyPredictionContext>(b)) {
return b; return b;
} }
} }
// convert singleton so both are arrays to normalize // convert singleton so both are arrays to normalize
if (dynamic_cast<SingletonPredictionContext*>(a) != nullptr) { if (is<SingletonPredictionContext>(a)) {
a = (PredictionContext *)new ArrayPredictionContext(static_cast<SingletonPredictionContext*>(a)); a.reset(new ArrayPredictionContext(std::dynamic_pointer_cast<SingletonPredictionContext>(a)));
} }
if (dynamic_cast<SingletonPredictionContext*>(b) != nullptr) { if (is<SingletonPredictionContext>(b)) {
b = (PredictionContext *)new ArrayPredictionContext(static_cast<SingletonPredictionContext*>(b)); b.reset(new ArrayPredictionContext(std::dynamic_pointer_cast<SingletonPredictionContext>(b)));
} }
return mergeArrays(static_cast<ArrayPredictionContext*>(a), static_cast<ArrayPredictionContext*>(b), rootIsWildcard, mergeCache); return mergeArrays(std::dynamic_pointer_cast<ArrayPredictionContext>(a),
std::dynamic_pointer_cast<ArrayPredictionContext>(b), rootIsWildcard, mergeCache);
} }
PredictionContext *PredictionContext::mergeSingletons(SingletonPredictionContext *a, SingletonPredictionContext *b, bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache) { PredictionContextRef PredictionContext::mergeSingletons(SingletonPredictionContextRef a,
if (mergeCache != nullptr) { SingletonPredictionContextRef b, bool rootIsWildcard, PredictionContextMergeCache *mergeCache) {
PredictionContext *previous = mergeCache->get(a,b);
if (previous != nullptr) { if (mergeCache != nullptr) { // Can be null if not given to the ATNState from which this call originates.
return previous; auto iterator = mergeCache->find({ a.get(), b.get() });
if (iterator != mergeCache->end()) {
return iterator->second;
} }
previous = mergeCache->get(b,a); iterator = mergeCache->find({ b.get(), a.get() });
if (previous != nullptr) { if (iterator != mergeCache->end()) {
return previous; return iterator->second;
} }
} }
PredictionContext *rootMerge = mergeRoot(a, b, rootIsWildcard); PredictionContextRef rootMerge = mergeRoot(a, b, rootIsWildcard);
if (rootMerge != nullptr) { if (rootMerge) {
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put((PredictionContext *)a, (PredictionContext *)b, rootMerge); (*mergeCache)[{ a.get(), b.get() }] = rootMerge;
} }
return rootMerge; return rootMerge;
} }
PredictionContextRef parentA = a->parent.lock();
PredictionContextRef parentB = b->parent.lock();
if (a->returnState == b->returnState) { // a == b if (a->returnState == b->returnState) { // a == b
PredictionContext *parent = merge(a->parent, b->parent, rootIsWildcard, mergeCache); PredictionContextRef parent = merge(parentA, parentB, rootIsWildcard, mergeCache);
// if parent is same as existing a or b parent or reduced to a parent, return it
if (parent == a->parent) { // ax + bx = ax, if a=b // If parent is same as existing a or b parent or reduced to a parent, return it.
return (PredictionContext *)a; if (parent == parentA) { // ax + bx = ax, if a=b
return a;
} }
if (parent == b->parent) { // ax + bx = bx, if a=b if (parent == parentB) { // ax + bx = bx, if a=b
return (PredictionContext *)b; return b;
} }
// else: ax + ay = a'[x,y] // else: ax + ay = a'[x,y]
// merge parents x and y, giving array node with x,y then remainders // merge parents x and y, giving array node with x,y then remainders
// of those graphs. dup a, a' points at merged array // of those graphs. dup a, a' points at merged array
// new joined parent so create new singleton pointing to it, a' // new joined parent so create new singleton pointing to it, a'
PredictionContext *a_ = (PredictionContext *)SingletonPredictionContext::create(parent, a->returnState); PredictionContextRef a_ = SingletonPredictionContext::create(parent, a->returnState);
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put((PredictionContext *)a, (PredictionContext *)b, a_); (*mergeCache)[{ a.get(), b.get() }] = a_;
} }
return a_; return a_;
} } else {
else { // a != b payloads differ // a != b payloads differ
// see if we can collapse parents due to $+x parents if local ctx // see if we can collapse parents due to $+x parents if local ctx
PredictionContext *singleParent = nullptr; std::weak_ptr<PredictionContext> singleParent;
if (a == b || (a->parent != nullptr && a->parent == b->parent)) { // ax + bx = [a,b]x if (a == b || (parentA && parentA == parentB)) { // ax + bx = [a,b]x
singleParent = a->parent; singleParent = a->parent;
} }
if (singleParent != nullptr) { // parents are same if (!singleParent.expired()) { // parents are same, sort payloads and use same parent
// sort payloads and use same parent
std::vector<int> payloads = { a->returnState, b->returnState }; std::vector<int> payloads = { a->returnState, b->returnState };
if (a->returnState > b->returnState) { if (a->returnState > b->returnState) {
payloads[0] = b->returnState; payloads[0] = b->returnState;
payloads[1] = a->returnState; payloads[1] = a->returnState;
} }
std::vector<PredictionContext *> parents = { singleParent, singleParent }; std::vector<std::weak_ptr<PredictionContext>> parents = { singleParent, singleParent };
PredictionContext *a_ = new ArrayPredictionContext(parents, payloads); PredictionContextRef a_(new ArrayPredictionContext(parents, payloads));
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a, b, a_); (*mergeCache)[{ a.get(), b.get() }] = a_;
} }
return a_; return a_;
} }
// parents differ and can't merge them. Just pack together // parents differ and can't merge them. Just pack together
// into array; can't merge. // into array; can't merge.
// ax + by = [ax,by] // ax + by = [ax,by]
PredictionContext *a_; PredictionContextRef a_;
if (a->returnState > b->returnState) { // sort by payload if (a->returnState > b->returnState) { // sort by payload
std::vector<int> payloads = { b->returnState, a->returnState }; std::vector<int> payloads = { b->returnState, a->returnState };
std::vector<PredictionContext *> parents = { b->parent, a->parent }; std::vector<std::weak_ptr<PredictionContext>> parents = { b->parent, a->parent };
a_ = new ArrayPredictionContext(parents, payloads); a_.reset(new ArrayPredictionContext(parents, payloads));
} else { } else {
std::vector<int> payloads = {a->returnState, b->returnState}; std::vector<int> payloads = {a->returnState, b->returnState};
std::vector<PredictionContext *> parents = { a->parent, b->parent }; std::vector<std::weak_ptr<PredictionContext>> parents = { a->parent, b->parent };
a_ = new ArrayPredictionContext(parents, payloads); a_.reset(new ArrayPredictionContext(parents, payloads));
} }
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a, b, a_); (*mergeCache)[{ a.get(), b.get() }] = a_;
} }
return a_; return a_;
} }
} }
PredictionContext *PredictionContext::mergeRoot(SingletonPredictionContext *a, SingletonPredictionContext *b, bool rootIsWildcard) { PredictionContextRef PredictionContext::mergeRoot(SingletonPredictionContextRef a, SingletonPredictionContextRef b,
bool rootIsWildcard) {
if (rootIsWildcard) { if (rootIsWildcard) {
if (a == EMPTY) { // * + b = * if (a == EMPTY) { // * + b = *
return (PredictionContext *)EMPTY; return EMPTY;
} }
if (b == EMPTY) { // a + * = * if (b == EMPTY) { // a + * = *
return (PredictionContext *)EMPTY; return EMPTY;
} }
} else { } else {
if (a == EMPTY && b == EMPTY) { // $ + $ = $ if (a == EMPTY && b == EMPTY) { // $ + $ = $
return (PredictionContext *)EMPTY; return EMPTY;
} }
if (a == EMPTY) { // $ + x = [$,x] if (a == EMPTY) { // $ + x = [$,x]
std::vector<int> payloads = { b->returnState, EMPTY_RETURN_STATE }; std::vector<int> payloads = { b->returnState, EMPTY_RETURN_STATE };
std::vector<PredictionContext *> parents = { b->parent, EMPTY }; std::vector<std::weak_ptr<PredictionContext>> parents = { b->parent, EMPTY };
PredictionContext *joined = new ArrayPredictionContext(parents, payloads); PredictionContextRef joined(new ArrayPredictionContext(parents, payloads));
return joined; return joined;
} }
if (b == EMPTY) { // x + $ = [$,x] ($ is always first if present) if (b == EMPTY) { // x + $ = [$,x] ($ is always first if present)
std::vector<int> payloads = { a->returnState, EMPTY_RETURN_STATE }; std::vector<int> payloads = { a->returnState, EMPTY_RETURN_STATE };
std::vector<PredictionContext *> parents = { a->parent, EMPTY }; std::vector<std::weak_ptr<PredictionContext>> parents = { a->parent, EMPTY };
PredictionContext *joined = new ArrayPredictionContext(parents, payloads); PredictionContextRef joined(new ArrayPredictionContext(parents, payloads));
return joined; return joined;
} }
} }
return nullptr; return nullptr;
} }
PredictionContext *PredictionContext::mergeArrays(ArrayPredictionContext *a, ArrayPredictionContext *b, bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache) { PredictionContextRef PredictionContext::mergeArrays(std::shared_ptr<ArrayPredictionContext> a,
std::shared_ptr<ArrayPredictionContext> b, bool rootIsWildcard, PredictionContextMergeCache *mergeCache) {
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
PredictionContext *previous = mergeCache->get(a,b); auto iterator = mergeCache->find({ a.get(), b.get() });
if (previous != nullptr) { if (iterator != mergeCache->end()) {
return previous; return iterator->second;
} }
previous = mergeCache->get(b,a); iterator = mergeCache->find({ b.get(), a.get() });
if (previous != nullptr) { if (iterator != mergeCache->end()) {
return previous; return iterator->second;
} }
} }
// merge sorted payloads a + b => M // merge sorted payloads a + b => M
std::vector<int>::size_type i = 0; // walks a size_t i = 0; // walks a
std::vector<int>::size_type j = 0; // walks b size_t j = 0; // walks b
std::vector<int>::size_type k = 0; // walks target M array size_t k = 0; // walks target M array
std::vector<int> mergedReturnStates; std::vector<int> mergedReturnStates;
std::vector<PredictionContext*> mergedParents; mergedReturnStates.resize(a->returnStates.size() + b->returnStates.size());
std::vector<std::weak_ptr<PredictionContext>> mergedParents;
mergedParents.resize(a->returnStates.size() + b->returnStates.size());
// walk and merge to yield mergedParents, mergedReturnStates // walk and merge to yield mergedParents, mergedReturnStates
while (i < a->returnStates.size() && j < b->returnStates.size()) { while (i < a->returnStates.size() && j < b->returnStates.size()) {
PredictionContext *a_parent = a->parents[i]; PredictionContextRef a_parent = a->parents[i].lock();
PredictionContext *b_parent = b->parents[j]; PredictionContextRef b_parent = b->parents[j].lock();
if (a->returnStates[i] == b->returnStates[j]) { if (a->returnStates[i] == b->returnStates[j]) {
// same payload (stack tops are equal), must yield merged singleton // same payload (stack tops are equal), must yield merged singleton
int payload = a->returnStates[i]; int payload = a->returnStates[i];
// $+$ = $ // $+$ = $
bool both$ = payload == EMPTY_RETURN_STATE && a_parent == nullptr && b_parent == nullptr; bool both$ = payload == EMPTY_RETURN_STATE && a_parent && b_parent;
bool ax_ax = (a_parent != nullptr && b_parent != nullptr) && a_parent == b_parent; // ax+ax -> ax bool ax_ax = (a_parent && b_parent) && a_parent == b_parent; // ax+ax -> ax
if (both$ || ax_ax) { if (both$ || ax_ax) {
mergedParents[k] = a_parent; // choose left mergedParents[k] = a_parent; // choose left
mergedReturnStates[k] = payload; mergedReturnStates[k] = payload;
} }
else { // ax+ay -> a'[x,y] else { // ax+ay -> a'[x,y]
PredictionContext *mergedParent = merge(a_parent, b_parent, rootIsWildcard, mergeCache); PredictionContextRef mergedParent = merge(a_parent, b_parent, rootIsWildcard, mergeCache);
mergedParents[k] = mergedParent; mergedParents[k] = mergedParent;
mergedReturnStates[k] = payload; mergedReturnStates[k] = payload;
} }
@ -332,9 +345,9 @@ PredictionContext *PredictionContext::mergeArrays(ArrayPredictionContext *a, Arr
// trim merged if we combined a few that had same stack tops // trim merged if we combined a few that had same stack tops
if (k < mergedParents.size()) { // write index < last position; trim if (k < mergedParents.size()) { // write index < last position; trim
if (k == 1) { // for just one merged element, return singleton top if (k == 1) { // for just one merged element, return singleton top
PredictionContext *a_ = SingletonPredictionContext::create(mergedParents[0], mergedReturnStates[0]); PredictionContextRef a_ = SingletonPredictionContext::create(mergedParents[0].lock(), mergedReturnStates[0]);
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a,b,a_); (*mergeCache)[{ a.get(), b.get() }] = a_;
} }
return a_; return a_;
} }
@ -342,48 +355,52 @@ PredictionContext *PredictionContext::mergeArrays(ArrayPredictionContext *a, Arr
mergedReturnStates = Arrays::copyOf(mergedReturnStates, k); mergedReturnStates = Arrays::copyOf(mergedReturnStates, k);
} }
PredictionContext *M = nullptr; std::shared_ptr<ArrayPredictionContext> M(new ArrayPredictionContext(mergedParents, mergedReturnStates));
// TODO: PredictionContext *M = new ArrayPredictionContext(mergedParents, mergedReturnStates);
// if we created same array as a or b, return that instead // if we created same array as a or b, return that instead
// TODO: track whether this is possible above during merge sort for speed // TO_DO: track whether this is possible above during merge sort for speed
if (M == a) { if (M == a) {
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a,b,a); (*mergeCache)[{ a.get(), b.get() }] = a;
} }
return a; return a;
} }
if (M == b) { if (M == b) {
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a,b,b); (*mergeCache)[{ a.get(), b.get() }] = b;
} }
return b; return b;
} }
combineCommonParents(mergedParents); if (combineCommonParents(mergedParents)) // Need to recreate the context as the parents array is copied on creation.
M.reset(new ArrayPredictionContext(mergedParents, mergedReturnStates));
if (mergeCache != nullptr) { if (mergeCache != nullptr) {
mergeCache->put(a,b,M); (*mergeCache)[{ a.get(), b.get() }] = M;
} }
return M; return M;
} }
void PredictionContext::combineCommonParents(std::vector<PredictionContext*> parents) { bool PredictionContext::combineCommonParents(std::vector<std::weak_ptr<PredictionContext>> &parents) {
std::unordered_map<PredictionContext*, PredictionContext*> uniqueParents = std::unordered_map<PredictionContext*, PredictionContext*>(); std::set<PredictionContextRef> uniqueParents;
for (size_t p = 0; p < parents.size(); p++) { for (size_t p = 0; p < parents.size(); p++) {
PredictionContext *parent = parents[p]; PredictionContextRef parent = parents[p].lock();
// ml: it's assumed that the == operator of PredictionContext kicks in here.
if (uniqueParents.find(parent) == uniqueParents.end()) { // don't replace if (uniqueParents.find(parent) == uniqueParents.end()) { // don't replace
uniqueParents[parent] = parent; uniqueParents.insert(parent);
} }
} }
for (size_t p = 0; p < parents.size(); p++) { if (uniqueParents.size() == parents.size())
parents[p] = uniqueParents.at(parents[p]); return false;
}
parents.clear();
std::copy(uniqueParents.begin(), uniqueParents.end(), parents.begin());
return true;
} }
std::wstring PredictionContext::toDOTString(PredictionContext *context) { std::wstring PredictionContext::toDOTString(PredictionContextRef context) {
if (context == nullptr) { if (context == nullptr) {
return L""; return L"";
} }
@ -391,24 +408,23 @@ std::wstring PredictionContext::toDOTString(PredictionContext *context) {
buf->append(L"digraph G {\n"); buf->append(L"digraph G {\n");
buf->append(L"rankdir=LR;\n"); buf->append(L"rankdir=LR;\n");
std::vector<PredictionContext*> nodes = getAllContextNodes(context); std::vector<PredictionContextRef> nodes = getAllContextNodes(context);
std::sort(nodes.begin(), nodes.end(), [](PredictionContextRef o1, PredictionContextRef o2) {
std::sort(nodes.begin(), nodes.end(), [](PredictionContext *o1, PredictionContext *o2) {
return o1->id - o2->id; return o1->id - o2->id;
}); });
for (auto current : nodes) { for (auto current : nodes) {
if (dynamic_cast<SingletonPredictionContext*>(current) != nullptr) { if (is<SingletonPredictionContext>(current)) {
std::wstring s = antlrcpp::StringConverterHelper::toString(current->id); std::wstring s = antlrcpp::StringConverterHelper::toString(current->id);
buf->append(L" s").append(s); buf->append(L" s").append(s);
std::wstring returnState = antlrcpp::StringConverterHelper::toString(current->getReturnState(0)); std::wstring returnState = antlrcpp::StringConverterHelper::toString(current->getReturnState(0));
if (dynamic_cast<EmptyPredictionContext*>(current) != nullptr) { if (is<EmptyPredictionContext>(current)) {
returnState = L"$"; returnState = L"$";
} }
buf->append(L" [label=\"").append(returnState).append(L"\"];\n"); buf->append(L" [label=\"").append(returnState).append(L"\"];\n");
continue; continue;
} }
ArrayPredictionContext *arr = static_cast<ArrayPredictionContext*>(current); std::shared_ptr<ArrayPredictionContext> arr = std::static_pointer_cast<ArrayPredictionContext>(current);
buf->append(L" s").append(arr->id); buf->append(L" s").append(arr->id);
buf->append(L" [shape=box, label=\""); buf->append(L" [shape=box, label=\"");
buf->append(L"["); buf->append(L"[");
@ -433,14 +449,14 @@ std::wstring PredictionContext::toDOTString(PredictionContext *context) {
continue; continue;
} }
for (size_t i = 0; i < current->size(); i++) { for (size_t i = 0; i < current->size(); i++) {
if (current->getParent(i) == nullptr) { if (current->getParent(i).expired()) {
continue; continue;
} }
std::wstring s = antlrcpp::StringConverterHelper::toString(current->id); std::wstring s = antlrcpp::StringConverterHelper::toString(current->id);
buf->append(L" s").append(s); buf->append(L" s").append(s);
buf->append(L"->"); buf->append(L"->");
buf->append(L"s"); buf->append(L"s");
buf->append(current->getParent(i)->id); buf->append(current->getParent(i).lock()->id);
if (current->size() > 1) { if (current->size() > 1) {
buf->append(std::wstring(L" [label=\"parent[") + antlrcpp::StringConverterHelper::toString(i) + std::wstring(L"]\"];\n")); buf->append(std::wstring(L" [label=\"parent[") + antlrcpp::StringConverterHelper::toString(i) + std::wstring(L"]\"];\n"));
} else { } else {
@ -453,35 +469,37 @@ std::wstring PredictionContext::toDOTString(PredictionContext *context) {
return buf->toString(); return buf->toString();
} }
PredictionContext *PredictionContext::getCachedContext(PredictionContext *context, PredictionContextCache *contextCache, // The "visited" map is just a temporary structure to control the retrieval process (which is recursive).
std::map<PredictionContext*, PredictionContext*> *visited) { PredictionContextRef PredictionContext::getCachedContext(PredictionContextRef context,
std::shared_ptr<PredictionContextCache> contextCache, std::map<PredictionContextRef, PredictionContextRef> &visited) {
if (context->isEmpty()) { if (context->isEmpty()) {
return context; return context;
} }
PredictionContext *existing = (*visited)[context]; {
if (existing != nullptr) { auto iterator = visited.find(context);
return existing; if (iterator != visited.end())
return iterator->second; // Not necessarly the same as context.
} }
existing = contextCache->get(context); auto iterator = contextCache->find(context);
if (existing != nullptr) { if (iterator != contextCache->end()) {
std::pair<PredictionContext*, PredictionContext*> thePair(context, existing); visited[context] = *iterator;
visited->insert(thePair);
return existing; return *iterator;
} }
bool changed = false; bool changed = false;
std::vector<PredictionContext*> parents; std::vector<std::weak_ptr<PredictionContext>> parents;
parents.resize(context->size());
for (size_t i = 0; i < parents.size(); i++) { for (size_t i = 0; i < parents.size(); i++) {
PredictionContext *parent = getCachedContext(context->getParent(i), contextCache, visited); std::weak_ptr<PredictionContext> parent = getCachedContext(context->getParent(i).lock(), contextCache, visited);
if (changed || parent != context->getParent(i)) { if (changed || parent.lock() != context->getParent(i).lock()) {
if (!changed) { if (!changed) {
parents = std::vector<PredictionContext*>(); parents.clear();
for (size_t j = 0; j < context->size(); j++) { for (size_t j = 0; j < context->size(); j++) {
parents[j] = context->getParent(j); parents.push_back(context->getParent(j));
} }
changed = true; changed = true;
@ -492,56 +510,49 @@ PredictionContext *PredictionContext::getCachedContext(PredictionContext *contex
} }
if (!changed) { if (!changed) {
contextCache->add(context); contextCache->insert(context);
std::pair<PredictionContext*, PredictionContext*> thePair(context,context); visited[context] = context;
visited->insert(thePair);
return context; return context;
} }
PredictionContext *updated; PredictionContextRef updated;
if (parents.empty()) { if (parents.empty()) {
updated = EMPTY; updated = EMPTY;
} else if (parents.size() == 1) { } else if (parents.size() == 1) {
updated = SingletonPredictionContext::create(parents[0], context->getReturnState(0)); updated = SingletonPredictionContext::create(parents[0], context->getReturnState(0));
} else { } else {
ArrayPredictionContext *arrayPredictionContext = static_cast<ArrayPredictionContext*>(context); updated = std::make_shared<ArrayPredictionContext>(parents, std::dynamic_pointer_cast<ArrayPredictionContext>(context)->returnStates);
updated = new ArrayPredictionContext(parents,
arrayPredictionContext->returnStates);
} }
contextCache->add(updated); contextCache->insert(updated);
visited[updated] = updated;
std::pair<PredictionContext*, PredictionContext*> thePair(updated, updated); visited[context] = updated;
visited->insert(thePair);
std::pair<PredictionContext*, PredictionContext*> otherPair(context, updated);
visited->insert(otherPair);
return updated; return updated;
} }
std::vector<PredictionContext*> PredictionContext::getAllContextNodes(PredictionContext *context) { std::vector<PredictionContextRef> PredictionContext::getAllContextNodes(PredictionContextRef context) {
std::vector<PredictionContext*> nodes = std::vector<PredictionContext*>(); std::vector<PredictionContextRef> nodes;
std::map<PredictionContext*, PredictionContext*> *visited = new std::map<PredictionContext*, PredictionContext*>(); std::map<PredictionContextRef, PredictionContextRef> visited;
getAllContextNodes_(context, nodes, visited); getAllContextNodes_(context, nodes, visited);
return nodes; return nodes;
} }
void PredictionContext::getAllContextNodes_(PredictionContext *context, std::vector<PredictionContext*> &nodes, std::map<PredictionContext*, PredictionContext*> *visited) { void PredictionContext::getAllContextNodes_(PredictionContextRef context,
std::vector<PredictionContextRef> &nodes,
std::map<PredictionContextRef, PredictionContextRef> &visited) {
if (context == nullptr || visited->at(context)) { if (visited.find(context) != visited.end()) {
return; return; // Already done.
} }
std::pair<PredictionContext*, PredictionContext*> thePair(context, context); visited[context] = context;
visited->insert(thePair);
nodes.push_back(context); nodes.push_back(context);
for (size_t i = 0; i < context->size(); i++) { for (size_t i = 0; i < context->size(); i++) {
getAllContextNodes_(context->getParent(i), nodes, visited); getAllContextNodes_(context->getParent(i).lock(), nodes, visited);
} }
} }
@ -559,7 +570,7 @@ std::vector<std::wstring> PredictionContext::toStrings(Recognizer *recognizer, i
return toStrings(recognizer, EMPTY, currentState); return toStrings(recognizer, EMPTY, currentState);
} }
std::vector<std::wstring> PredictionContext::toStrings(Recognizer *recognizer, PredictionContext *stop, int currentState) { std::vector<std::wstring> PredictionContext::toStrings(Recognizer *recognizer, PredictionContextRef stop, int currentState) {
std::vector<std::wstring> result; std::vector<std::wstring> result;
@ -568,11 +579,11 @@ std::vector<std::wstring> PredictionContext::toStrings(Recognizer *recognizer, P
bool last = true; bool last = true;
PredictionContext *p = this; PredictionContext *p = this;
int stateNumber = currentState; int stateNumber = currentState;
antlrcpp::StringBuilder *localBuffer = new antlrcpp::StringBuilder(); antlrcpp::StringBuilder localBuffer;
localBuffer->append(L"["); localBuffer.append(L"[");
bool outerContinue = false; bool outerContinue = false;
while (!p->isEmpty() && p != stop) { while (!p->isEmpty() && p != stop.get()) {
size_t index = 0; size_t index = 0;
if (p->size() > 0) { if (p->size() > 0) {
size_t bits = 1; size_t bits = 1;
@ -591,34 +602,34 @@ std::vector<std::wstring> PredictionContext::toStrings(Recognizer *recognizer, P
} }
if (recognizer != nullptr) { if (recognizer != nullptr) {
if (localBuffer->length() > 1) { if (localBuffer.length() > 1) {
// first char is '[', if more than that this isn't the first rule // first char is '[', if more than that this isn't the first rule
localBuffer->append(L' '); localBuffer.append(L' ');
} }
const ATN &atn = recognizer->getATN(); const ATN &atn = recognizer->getATN();
ATNState *s = atn.states[(size_t)stateNumber]; ATNState *s = atn.states[(size_t)stateNumber];
std::wstring ruleName = recognizer->getRuleNames()[(size_t)s->ruleIndex]; std::wstring ruleName = recognizer->getRuleNames()[(size_t)s->ruleIndex];
localBuffer->append(ruleName); localBuffer.append(ruleName);
} else if (p->getReturnState(index) != EMPTY_RETURN_STATE) { } else if (p->getReturnState(index) != EMPTY_RETURN_STATE) {
if (!p->isEmpty()) { if (!p->isEmpty()) {
if (localBuffer->length() > 1) { if (localBuffer.length() > 1) {
// first char is '[', if more than that this isn't the first rule // first char is '[', if more than that this isn't the first rule
localBuffer->append(L' '); localBuffer.append(L' ');
} }
localBuffer->append(p->getReturnState(index)); localBuffer.append(p->getReturnState(index));
} }
} }
stateNumber = p->getReturnState(index); stateNumber = p->getReturnState(index);
p = p->getParent(index); p = p->getParent(index).lock().get();
} }
if (outerContinue) if (outerContinue)
continue; continue;
localBuffer->append(L"]"); localBuffer.append(L"]");
result.push_back(localBuffer->toString()); result.push_back(localBuffer.toString());
if (last) { if (last) {
break; break;

View File

@ -43,19 +43,20 @@ namespace v4 {
namespace runtime { namespace runtime {
namespace atn { namespace atn {
class PredictionContext { typedef std::set<PredictionContextRef> PredictionContextCache;
/// <summary>
/// Represents {@code $} in local context prediction, which means wildcard.
/// {@code *+x = *}.
/// </summary>
public:
static EmptyPredictionContext * EMPTY;
/// <summary> // For the keys we use raw pointers, as we don't need to access them.
/// Represents {@code $} in an array in full context mode, when {@code $} typedef std::map<std::pair<PredictionContext *, PredictionContext *>, PredictionContextRef> PredictionContextMergeCache;
/// doesn't mean wildcard: {@code $ + x = [$,x]}. Here,
/// {@code $} = <seealso cref="#EMPTY_RETURN_STATE"/>. class PredictionContext {
/// </summary> public:
/// Represents $ in local context prediction, which means wildcard.
/// *+x = *.
static const std::shared_ptr<EmptyPredictionContext> EMPTY;
/// Represents $ in an array in full context mode, when $
/// doesn't mean wildcard: $ + x = [$,x]. Here,
/// $ = EMPTY_RETURN_STATE.
static const int EMPTY_RETURN_STATE = INT16_MAX; static const int EMPTY_RETURN_STATE = INT16_MAX;
private: private:
@ -94,10 +95,10 @@ namespace atn {
public: public:
/// Convert a RuleContext tree to a PredictionContext graph. /// Convert a RuleContext tree to a PredictionContext graph.
/// Return EMPTY if outerContext is empty. /// Return EMPTY if outerContext is empty.
static PredictionContext *fromRuleContext(const ATN &atn, RuleContext *outerContext); static PredictionContextRef fromRuleContext(const ATN &atn, RuleContext *outerContext);
virtual size_t size() const = 0; virtual size_t size() const = 0;
virtual PredictionContext *getParent(size_t index) const = 0; virtual std::weak_ptr<PredictionContext> getParent(size_t index) const = 0;
virtual int getReturnState(size_t index) const = 0; virtual int getReturnState(size_t index) const = 0;
virtual bool operator == (const PredictionContext &o) const = 0; virtual bool operator == (const PredictionContext &o) const = 0;
@ -110,12 +111,13 @@ namespace atn {
protected: protected:
static size_t calculateEmptyHashCode(); static size_t calculateEmptyHashCode();
static size_t calculateHashCode(PredictionContext *parent, int returnState); static size_t calculateHashCode(std::weak_ptr<PredictionContext> parent, int returnState);
static size_t calculateHashCode(const std::vector<PredictionContext*> &parents, const std::vector<int> &returnStates); static size_t calculateHashCode(const std::vector<std::weak_ptr<PredictionContext>> &parents, const std::vector<int> &returnStates);
public: public:
// dispatch // dispatch
static PredictionContext *merge(PredictionContext *a, PredictionContext *b, bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache); static PredictionContextRef merge(PredictionContextRef a,
PredictionContextRef b, bool rootIsWildcard, PredictionContextMergeCache *mergeCache);
/// <summary> /// <summary>
/// Merge two <seealso cref="SingletonPredictionContext"/> instances. /// Merge two <seealso cref="SingletonPredictionContext"/> instances.
@ -151,7 +153,8 @@ namespace atn {
/// <param name="rootIsWildcard"> {@code true} if this is a local-context merge, /// <param name="rootIsWildcard"> {@code true} if this is a local-context merge,
/// otherwise false to indicate a full-context merge </param> /// otherwise false to indicate a full-context merge </param>
/// <param name="mergeCache"> </param> /// <param name="mergeCache"> </param>
static PredictionContext *mergeSingletons(SingletonPredictionContext *a, SingletonPredictionContext *b, bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache); static PredictionContextRef mergeSingletons(SingletonPredictionContextRef a, SingletonPredictionContextRef b,
bool rootIsWildcard, PredictionContextMergeCache *mergeCache);
/// <summary> /// <summary>
/// Handle case where at least one of {@code a} or {@code b} is /// Handle case where at least one of {@code a} or {@code b} is
@ -202,7 +205,8 @@ namespace atn {
/// <param name="b"> the second <seealso cref="SingletonPredictionContext"/> </param> /// <param name="b"> the second <seealso cref="SingletonPredictionContext"/> </param>
/// <param name="rootIsWildcard"> {@code true} if this is a local-context merge, /// <param name="rootIsWildcard"> {@code true} if this is a local-context merge,
/// otherwise false to indicate a full-context merge </param> /// otherwise false to indicate a full-context merge </param>
static PredictionContext *mergeRoot(SingletonPredictionContext *a, SingletonPredictionContext *b, bool rootIsWildcard); static PredictionContextRef mergeRoot(SingletonPredictionContextRef a, SingletonPredictionContextRef b,
bool rootIsWildcard);
/// <summary> /// <summary>
/// Merge two <seealso cref="ArrayPredictionContext"/> instances. /// Merge two <seealso cref="ArrayPredictionContext"/> instances.
@ -233,52 +237,31 @@ namespace atn {
/// <seealso cref="SingletonPredictionContext"/>.<br/> /// <seealso cref="SingletonPredictionContext"/>.<br/>
/// <embed src="images/ArrayMerge_EqualTop.svg" type="image/svg+xml"/> /// <embed src="images/ArrayMerge_EqualTop.svg" type="image/svg+xml"/>
/// </summary> /// </summary>
static PredictionContext *mergeArrays(ArrayPredictionContext *a, ArrayPredictionContext *b, bool rootIsWildcard, misc::DoubleKeyMap<PredictionContext*, PredictionContext*, PredictionContext*> *mergeCache); static PredictionContextRef mergeArrays(std::shared_ptr<ArrayPredictionContext> a,
std::shared_ptr<ArrayPredictionContext> b, bool rootIsWildcard, PredictionContextMergeCache *mergeCache);
/// <summary>
/// Make pass over all <em>M</em> {@code parents}; merge any {@code ()}
/// ones.
/// </summary>
protected: protected:
static void combineCommonParents(std::vector<PredictionContext*>parents); /// Make pass over all M parents; merge any equal() ones.
/// @returns true if the list has been changed (i.e. duplicates where found).
static bool combineCommonParents(std::vector<std::weak_ptr<PredictionContext>> &parents);
public: public:
static std::wstring toDOTString(PredictionContext *context); static std::wstring toDOTString(PredictionContextRef context);
static PredictionContext *getCachedContext(PredictionContext *context, PredictionContextCache *contextCache, std::map<PredictionContext*, PredictionContext*> *visited); static PredictionContextRef getCachedContext(PredictionContextRef context,
std::shared_ptr<PredictionContextCache> contextCache,
// // extra structures, but cut/paste/morphed works, so leave it. std::map<PredictionContextRef, PredictionContextRef> &visited);
// // seems to do a breadth-first walk
// public static List<PredictionContext> getAllNodes(PredictionContext context) {
// Map<PredictionContext, PredictionContext> visited =
// new IdentityHashMap<PredictionContext, PredictionContext>();
// Deque<PredictionContext> workList = new ArrayDeque<PredictionContext>();
// workList.add(context);
// visited.put(context, context);
// List<PredictionContext> nodes = new ArrayList<PredictionContext>();
// while (!workList.isEmpty()) {
// PredictionContext current = workList.pop();
// nodes.add(current);
// for (int i = 0; i < current.size(); i++) {
// PredictionContext parent = current.getParent(i);
// if ( parent!=null && visited.put(parent, parent) == null) {
// workList.push(parent);
// }
// }
// }
// return nodes;
// }
// ter's recursive version of Sam's getAllNodes() // ter's recursive version of Sam's getAllNodes()
static std::vector<PredictionContext*> getAllContextNodes(PredictionContext *context); static std::vector<PredictionContextRef> getAllContextNodes(PredictionContextRef context);
static void getAllContextNodes_(PredictionContextRef context,
static void getAllContextNodes_(PredictionContext *context, std::vector<PredictionContext*> &nodes, std::map<PredictionContext*, PredictionContext*> *visited); std::vector<PredictionContextRef> &nodes, std::map<PredictionContextRef, PredictionContextRef> &visited);
std::wstring toString(); std::wstring toString();
std::wstring toString(Recognizer *recog); std::wstring toString(Recognizer *recog);
std::vector<std::wstring> toStrings(Recognizer *recognizer, int currentState); std::vector<std::wstring> toStrings(Recognizer *recognizer, int currentState);
std::vector<std::wstring> toStrings(Recognizer *recognizer, PredictionContext *stop, int currentState); std::vector<std::wstring> toStrings(Recognizer *recognizer, PredictionContextRef stop, int currentState);
}; };
} // namespace atn } // namespace atn
@ -294,7 +277,7 @@ namespace std {
template <> struct hash<PredictionContext> template <> struct hash<PredictionContext>
{ {
size_t operator () (PredictionContext &x) const size_t operator () (const PredictionContext &x) const
{ {
return x.hashCode(); return x.hashCode();
} }

View File

@ -1,61 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2015 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "EmptyPredictionContext.h"
#include "PredictionContextCache.h"
using namespace org::antlr::v4::runtime::atn;
org::antlr::v4::runtime::atn::PredictionContext *PredictionContextCache::add(
PredictionContext *ctx) {
if (ctx == PredictionContext::EMPTY) {
return PredictionContext::EMPTY;
}
PredictionContext *existing = cache->at(ctx);
if (existing != nullptr) {
// System.out.println(name+" reuses "+existing);
return existing;
}
cache->insert(std::pair<PredictionContext *, PredictionContext *>(ctx, ctx));
return ctx;
}
org::antlr::v4::runtime::atn::PredictionContext *PredictionContextCache::get(
PredictionContext *ctx) {
return cache->at(ctx);
}
size_t PredictionContextCache::size() { return cache->size(); }
void PredictionContextCache::InitializeInstanceFields() {
cache = new std::map<PredictionContext *, PredictionContext *>();
}

View File

@ -1,73 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace atn {
/// <summary>
/// Used to cache <seealso cref="PredictionContext"/> objects. Its used for the
/// shared
/// context cash associated with contexts in DFA states. This cache
/// can be used for both lexers and parsers.
/// </summary>
class PredictionContextCache {
protected:
std::map<PredictionContext *, PredictionContext *> *cache;
/// <summary>
/// Add a context to the cache and return it. If the context already exists,
/// return that one instead and do not add a new context to the cache.
/// Protect shared cache from unsafe thread access.
/// </summary>
public:
virtual PredictionContext *add(PredictionContext *ctx);
virtual PredictionContext *get(PredictionContext *ctx);
virtual size_t size();
private:
void InitializeInstanceFields();
public:
PredictionContextCache() { InitializeInstanceFields(); }
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -44,7 +44,7 @@ struct AltAndContextConfigHasher
size_t operator () (const ATNConfig &o) const { size_t operator () (const ATNConfig &o) const {
size_t hashCode = misc::MurmurHash::initialize(7); size_t hashCode = misc::MurmurHash::initialize(7);
hashCode = misc::MurmurHash::update(hashCode, (size_t)o.state->stateNumber); hashCode = misc::MurmurHash::update(hashCode, (size_t)o.state->stateNumber);
hashCode = misc::MurmurHash::update(hashCode, (size_t)o.context); hashCode = misc::MurmurHash::update(hashCode, (size_t)o.context.get());
return misc::MurmurHash::finish(hashCode, 2); return misc::MurmurHash::finish(hashCode, 2);
} }
}; };
@ -77,7 +77,7 @@ bool PredictionModeClass::hasSLLConflictTerminatingPrediction(PredictionMode* mo
// since we'll often fail over anyway. // since we'll often fail over anyway.
if (configs->hasSemanticContext) { if (configs->hasSemanticContext) {
// dup configs, tossing out semantic predicates // dup configs, tossing out semantic predicates
ATNConfigSet* dup = new ATNConfigSet(); ATNConfigSet* dup = new ATNConfigSet(true, std::shared_ptr<ConfigLookup>());
for (ATNConfig config : *configs->configLookup) { for (ATNConfig config : *configs->configLookup) {
ATNConfig* c = new ATNConfig(&config, SemanticContext::NONE); ATNConfig* c = new ATNConfig(&config, SemanticContext::NONE);
dup->add(c); dup->add(c);

View File

@ -30,10 +30,12 @@
*/ */
#include "MurmurHash.h" #include "MurmurHash.h"
#include "CPPUtils.h"
#include "SemanticContext.h" #include "SemanticContext.h"
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
using namespace antlrcpp;
SemanticContext::Predicate::Predicate() : Predicate(-1, -1, false) { SemanticContext::Predicate::Predicate() : Predicate(-1, -1, false) {
} }
@ -97,38 +99,35 @@ std::wstring SemanticContext::PrecedencePredicate::toString() const {
} }
SemanticContext::AND::AND(SemanticContext *a, SemanticContext *b) { SemanticContext::AND::AND(SemanticContextRef a, SemanticContextRef b) {
std::vector<SemanticContext*> *operands = new std::vector<SemanticContext*>();
if (dynamic_cast<AND*>(a) != nullptr) { if (is<AND>(a)) {
const std::vector<SemanticContext*> op = ((AND*)a)->opnds; const std::vector<SemanticContextRef> op = ((AND*)a.get())->opnds;
for (auto var : op) { for (auto var : op) {
operands->insert(op.end(), var); opnds.push_back(var);
} }
} else { } else {
operands->insert(operands->end(), a); opnds.push_back(a);
}
if (dynamic_cast<AND*>(b) != nullptr) {
const std::vector<SemanticContext*> op = ((AND*)b)->opnds;
for (auto var : op) {
operands->insert(op.end(), var);
}
} else {
operands->insert(operands->end(), b);
} }
std::vector<PrecedencePredicate*> precedencePredicates = filterPrecedencePredicates<SemanticContext*>(operands); if (is<AND>(b)) {
const std::vector<SemanticContextRef> op = ((AND*)b.get())->opnds;
for (auto var : op) {
opnds.push_back(var);
}
} else {
opnds.push_back(b);
}
std::vector<std::shared_ptr<PrecedencePredicate>> precedencePredicates = filterPrecedencePredicates(opnds);
if (!precedencePredicates.empty()) { if (!precedencePredicates.empty()) {
// interested in the transition with the lowest precedence // interested in the transition with the lowest precedence
PrecedencePredicate *reduced = std::min_element(*precedencePredicates.begin(), auto predicate = [](std::shared_ptr<PrecedencePredicate> a, std::shared_ptr<PrecedencePredicate> b) {
*precedencePredicates.end(), return a->precedence < b->precedence;
(*SemanticContext::PrecedencePredicate::lessThan)); };
operands->insert(operands->end(), reduced); auto reduced = std::min_element(precedencePredicates.begin(), precedencePredicates.end(), predicate);
} opnds.push_back(*reduced);
for (auto op : *operands) {
opnds.insert(opnds.end(), op);
} }
} }
@ -144,7 +143,7 @@ bool SemanticContext::AND::operator == (const SemanticContext &other) const {
size_t SemanticContext::AND::hashCode() { size_t SemanticContext::AND::hashCode() {
return misc::MurmurHash::hashCode(opnds.data(), opnds.size(), typeid(AND).hash_code()); return misc::MurmurHash::hashCode(opnds, typeid(AND).hash_code());
} }
@ -157,38 +156,34 @@ std::wstring SemanticContext::AND::toString() const {
return tmp; return tmp;
} }
SemanticContext::OR::OR(SemanticContext *a, SemanticContext *b){ SemanticContext::OR::OR(SemanticContextRef a, SemanticContextRef b){
std::vector<SemanticContext*> *operands = new std::vector<SemanticContext*>();
//opnds = operands::toArray(new SemanticContext[operands->size()]); if (is<OR>(a)) {
const std::vector<SemanticContextRef> op = ((OR*)a.get())->opnds;
if (dynamic_cast<OR*>(a) != nullptr) {
const std::vector<SemanticContext*> op = ((OR*)a)->opnds;
for (auto var : op) { for (auto var : op) {
operands->insert(op.end(), var); opnds.push_back(var);
} }
} else { } else {
operands->insert(operands->end(), a); opnds.push_back(a);
}
if (dynamic_cast<OR*>(b) != nullptr) {
const std::vector<SemanticContext*> op = ((OR*)b)->opnds;
for (auto var : op) {
operands->insert(op.end(), var);
}
} else {
operands->insert(operands->end(), b);
} }
std::vector<PrecedencePredicate*> precedencePredicates = filterPrecedencePredicates(operands); if (is<OR>(b)) {
const std::vector<SemanticContextRef> op = ((OR*)b.get())->opnds;
for (auto var : op) {
opnds.push_back(var);
}
} else {
opnds.push_back(b);
}
std::vector<std::shared_ptr<PrecedencePredicate>> precedencePredicates = filterPrecedencePredicates(opnds);
if (!precedencePredicates.empty()) { if (!precedencePredicates.empty()) {
// interested in the transition with the highest precedence // interested in the transition with the highest precedence
PrecedencePredicate *reduced = std::max_element(*precedencePredicates.begin(), auto predicate = [](std::shared_ptr<PrecedencePredicate> a, std::shared_ptr<PrecedencePredicate> b) {
*precedencePredicates.end(), return a->precedence > b->precedence;
(*SemanticContext::PrecedencePredicate::greaterThan)); };
operands->insert(operands->end(), reduced); auto reduced = std::min_element(precedencePredicates.begin(), precedencePredicates.end(), predicate);
} opnds.push_back(*reduced);
for (auto op : *operands) {
opnds.insert(opnds.end(), op);
} }
} }
@ -203,7 +198,7 @@ bool SemanticContext::OR::operator == (const SemanticContext &other) const {
} }
size_t SemanticContext::OR::hashCode() { size_t SemanticContext::OR::hashCode() {
return misc::MurmurHash::hashCode(opnds.data(), opnds.size(), typeid(OR).hash_code()); return misc::MurmurHash::hashCode(opnds, typeid(OR).hash_code());
} }
@ -215,16 +210,18 @@ std::wstring SemanticContext::OR::toString() const {
return tmp; return tmp;
} }
SemanticContext *const SemanticContext::NONE = new Predicate(); const SemanticContextRef SemanticContext::NONE = std::make_shared<SemanticContext::Predicate>(-1, -1, false);
SemanticContext *SemanticContext::And(SemanticContext *a, SemanticContext *b) { SemanticContextRef SemanticContext::And(SemanticContextRef a, SemanticContextRef b) {
if (a == nullptr || a == NONE) { if (!a || a == NONE) {
return b; return b;
} }
if (b == nullptr || b == NONE) {
if (!b || b == NONE) {
return a; return a;
} }
AND *result = new AND(a, b);
std::shared_ptr<AND> result = std::make_shared<AND>(a, b);
if (result->opnds.size() == 1) { if (result->opnds.size() == 1) {
return result->opnds[0]; return result->opnds[0];
} }
@ -232,17 +229,19 @@ SemanticContext *SemanticContext::And(SemanticContext *a, SemanticContext *b) {
return result; return result;
} }
SemanticContext *SemanticContext::Or(SemanticContext *a, SemanticContext *b) { SemanticContextRef SemanticContext::Or(SemanticContextRef a, SemanticContextRef b) {
if (a == nullptr) { if (!a) {
return b; return b;
} }
if (b == nullptr) { if (!b) {
return a; return a;
} }
if (a == NONE || b == NONE) { if (a == NONE || b == NONE) {
return NONE; return NONE;
} }
OR *result = new OR(a, b);
std::shared_ptr<OR> result = std::make_shared<OR>(a, b);
if (result->opnds.size() == 1) { if (result->opnds.size() == 1) {
return result->opnds[0]; return result->opnds[0];
} }

View File

@ -32,6 +32,7 @@
#pragma once #pragma once
#include "Recognizer.h" #include "Recognizer.h"
#include "CPPUtils.h"
namespace org { namespace org {
namespace antlr { namespace antlr {
@ -39,18 +40,16 @@ namespace v4 {
namespace runtime { namespace runtime {
namespace atn { namespace atn {
/// <summary>
/// A tree structure used to record the semantic context in which /// A tree structure used to record the semantic context in which
/// an ATN configuration is valid. It's either a single predicate, /// an ATN configuration is valid. It's either a single predicate,
/// a conjunction {@code p1&&p2}, or a sum of products {@code p1||p2}. /// a conjunction "p1 && p2", or a sum of products "p1||p2".
/// <p/> ///
/// I have scoped the <seealso cref="AND"/>, <seealso cref="OR"/>, and <seealso cref="Predicate"/> subclasses of /// I have scoped the AND, OR, and Predicate subclasses of
/// <seealso cref="SemanticContext"/> within the scope of this outer class. /// SemanticContext within the scope of this outer class.
/// </summary>
class SemanticContext { class SemanticContext {
public: public:
SemanticContext *parent; //SemanticContext *parent;
static SemanticContext *const NONE; static const SemanticContextRef NONE;
virtual size_t hashCode() = 0; virtual size_t hashCode() = 0;
virtual std::wstring toString() const = 0; virtual std::wstring toString() const = 0;
@ -71,10 +70,10 @@ namespace atn {
/// </summary> /// </summary>
virtual bool eval(Recognizer *parser, RuleContext *outerContext) = 0; virtual bool eval(Recognizer *parser, RuleContext *outerContext) = 0;
static SemanticContext *And(SemanticContext *a, SemanticContext *b); static SemanticContextRef And(SemanticContextRef a, SemanticContextRef b);
/// See also: ParserATNSimulator::getPredsForAmbigAlts. /// See also: ParserATNSimulator::getPredsForAmbigAlts.
static SemanticContext *Or(SemanticContext *a, SemanticContext *b); static SemanticContextRef Or(SemanticContextRef a, SemanticContextRef b);
class Predicate; class Predicate;
class PrecedencePredicate; class PrecedencePredicate;
@ -82,13 +81,12 @@ namespace atn {
class OR; class OR;
private: private:
template<typename T1> // where T1 : SemanticContext template<typename T1> // where T1 : SemanticContextRef
static std::vector<PrecedencePredicate*> filterPrecedencePredicates(std::vector<T1> *collection) { static std::vector<std::shared_ptr<PrecedencePredicate>> filterPrecedencePredicates(const std::vector<T1> &collection) {
std::vector<PrecedencePredicate*> result; std::vector<std::shared_ptr<PrecedencePredicate>> result;
for (std::vector<SemanticContext*>::const_iterator iterator = collection->begin(); iterator != collection->end(); ++iterator) { for (auto context : collection) {
SemanticContext *context = *iterator; if (antlrcpp::is<PrecedencePredicate>(context)) {
if ((PrecedencePredicate*)(context) != nullptr) { result.push_back(std::dynamic_pointer_cast<PrecedencePredicate>(context));
result.push_back((PrecedencePredicate*)context);
} }
} }
@ -140,21 +138,13 @@ namespace atn {
virtual size_t hashCode() override; virtual size_t hashCode() override;
virtual bool operator == (const SemanticContext &other) const override; virtual bool operator == (const SemanticContext &other) const override;
virtual std::wstring toString() const override; virtual std::wstring toString() const override;
static bool lessThan(const PrecedencePredicate &a, const PrecedencePredicate &b) {
return a.precedence < b.precedence;
}
static bool greaterThan(const PrecedencePredicate &a,
const PrecedencePredicate &b) {
return a.precedence > b.precedence;
}
}; };
class SemanticContext::AND : public SemanticContext { class SemanticContext::AND : public SemanticContext {
public: public:
std::vector<SemanticContext*> opnds; std::vector<SemanticContextRef> opnds;
AND(SemanticContext *a, SemanticContext *b); AND(SemanticContextRef a, SemanticContextRef b);
virtual bool operator == (const SemanticContext &other) const override; virtual bool operator == (const SemanticContext &other) const override;
virtual size_t hashCode() override; virtual size_t hashCode() override;
@ -174,9 +164,9 @@ namespace atn {
class SemanticContext::OR : public SemanticContext { class SemanticContext::OR : public SemanticContext {
public: public:
std::vector<SemanticContext*> opnds; std::vector<SemanticContextRef> opnds;
OR(SemanticContext *a, SemanticContext *b); OR(SemanticContextRef a, SemanticContextRef b);
virtual bool operator == (const SemanticContext &other) const override; virtual bool operator == (const SemanticContext &other) const override;
virtual size_t hashCode() override; virtual size_t hashCode() override;

View File

@ -29,29 +29,32 @@
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/ */
#include "EmptyPredictionContext.h"
#include "stringconverter.h" #include "stringconverter.h"
#include "SingletonPredictionContext.h" #include "SingletonPredictionContext.h"
using namespace org::antlr::v4::runtime::atn; using namespace org::antlr::v4::runtime::atn;
SingletonPredictionContext::SingletonPredictionContext(PredictionContext *parent, int returnState) : PredictionContext(parent != nullptr ? calculateHashCode(parent, returnState) : calculateEmptyHashCode()), parent(parent), returnState(returnState) { SingletonPredictionContext::SingletonPredictionContext(std::weak_ptr<PredictionContext> parent, int returnState)
: PredictionContext(!parent.expired() ? calculateHashCode(parent, returnState) : calculateEmptyHashCode()),
parent(parent), returnState(returnState) {
assert(returnState != ATNState::INVALID_STATE_NUMBER); assert(returnState != ATNState::INVALID_STATE_NUMBER);
} }
SingletonPredictionContext *SingletonPredictionContext::create(PredictionContext *parent, int returnState) { SingletonPredictionContextRef SingletonPredictionContext::create(std::weak_ptr<PredictionContext> parent, int returnState) {
if (returnState == EMPTY_RETURN_STATE && parent == nullptr) { if (returnState == EMPTY_RETURN_STATE && parent.expired()) {
// someone can pass in the bits of an array ctx that mean $ // someone can pass in the bits of an array ctx that mean $
return (atn::SingletonPredictionContext *)EMPTY; return EMPTY;
} }
return new SingletonPredictionContext(parent, returnState); return std::make_shared<SingletonPredictionContext>(parent, returnState);
} }
size_t SingletonPredictionContext::size() const { size_t SingletonPredictionContext::size() const {
return 1; return 1;
} }
PredictionContext *SingletonPredictionContext::getParent(size_t index) const { std::weak_ptr<PredictionContext> SingletonPredictionContext::getParent(size_t index) const {
assert(index == 0); assert(index == 0);
return parent; return parent;
} }
@ -75,11 +78,11 @@ bool SingletonPredictionContext::operator == (const PredictionContext &o) const
return false; // can't be same if hash is different return false; // can't be same if hash is different
} }
return returnState == other->returnState && (parent != nullptr && parent == other->parent); return returnState == other->returnState && (!parent.expired() && parent.lock() == other->parent.lock());
} }
std::wstring SingletonPredictionContext::toString() const { std::wstring SingletonPredictionContext::toString() const {
std::wstring up = parent != nullptr ? parent->toString() : L""; std::wstring up = !parent.expired() ? parent.lock()->toString() : L"";
if (up.length() == 0) { if (up.length() == 0) {
if (returnState == EMPTY_RETURN_STATE) { if (returnState == EMPTY_RETURN_STATE) {
return L"$"; return L"$";

View File

@ -41,15 +41,15 @@ namespace atn {
class SingletonPredictionContext : public PredictionContext { class SingletonPredictionContext : public PredictionContext {
public: public:
PredictionContext *const parent; const std::weak_ptr<PredictionContext> parent;
const int returnState; const int returnState;
SingletonPredictionContext(PredictionContext *parent, int returnState); SingletonPredictionContext(std::weak_ptr<PredictionContext> parent, int returnState);
static SingletonPredictionContext *create(PredictionContext *parent, int returnState); static SingletonPredictionContextRef create(std::weak_ptr<PredictionContext> parent, int returnState);
virtual size_t size() const override; virtual size_t size() const override;
virtual PredictionContext *getParent(size_t index) const override; virtual std::weak_ptr<PredictionContext> getParent(size_t index) const override;
virtual int getReturnState(size_t index) const override; virtual int getReturnState(size_t index) const override;
virtual bool operator == (const PredictionContext &o) const override; virtual bool operator == (const PredictionContext &o) const override;
virtual std::wstring toString() const; virtual std::wstring toString() const;

View File

@ -53,8 +53,8 @@ namespace atn {
/// ATN transitions. /// ATN transitions.
/// </summary> /// </summary>
class Transition { class Transition {
// constants for serialization
public: public:
// constants for serialization
static const int EPSILON = 1; static const int EPSILON = 1;
static const int RANGE = 2; static const int RANGE = 2;
static const int RULE = 3; static const int RULE = 3;
@ -82,9 +82,7 @@ namespace atn {
/// <summary> /// <summary>
/// Are we epsilon, action, sempred? </summary> /// Are we epsilon, action, sempred? </summary>
virtual bool isEpsilon() const; virtual bool isEpsilon() const;
virtual misc::IntervalSet label() const; virtual misc::IntervalSet label() const;
virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const = 0; virtual bool matches(int symbol, int minVocabSymbol, int maxVocabSymbol) const = 0;
}; };

View File

@ -37,11 +37,11 @@
#include "DFAState.h" #include "DFAState.h"
using namespace org::antlr::v4::runtime::dfa; using namespace org::antlr::v4::runtime::dfa;
using namespace org::antlr::v4::runtime::atn;
DFAState::PredPrediction::PredPrediction(atn::SemanticContext *pred, int alt) { DFAState::PredPrediction::PredPrediction(SemanticContextRef pred, int alt) : pred(pred) {
InitializeInstanceFields(); InitializeInstanceFields();
this->alt = alt; this->alt = alt;
this->pred = pred;
} }
std::wstring DFAState::PredPrediction::toString() { std::wstring DFAState::PredPrediction::toString() {
@ -55,7 +55,7 @@ void DFAState::PredPrediction::InitializeInstanceFields() {
DFAState::DFAState() : DFAState(-1) { DFAState::DFAState() : DFAState(-1) {
} }
DFAState::DFAState(int stateNumber) : DFAState(new atn::ATNConfigSet(), stateNumber) { DFAState::DFAState(int stateNumber) : DFAState(new atn::ATNConfigSet(true, std::shared_ptr<ConfigLookup>()), stateNumber) {
} }
DFAState::DFAState(atn::ATNConfigSet *configs, int stateNumber) : configs(configs), stateNumber(stateNumber) { DFAState::DFAState(atn::ATNConfigSet *configs, int stateNumber) : configs(configs), stateNumber(stateNumber) {

View File

@ -66,9 +66,9 @@ namespace dfa {
public: public:
class PredPrediction { class PredPrediction {
public: public:
atn::SemanticContext *pred; // never null; at least SemanticContext.NONE std::shared_ptr<atn::SemanticContext> pred; // never null; at least SemanticContext.NONE
int alt; int alt;
PredPrediction(atn::SemanticContext *pred, int alt); PredPrediction(std::shared_ptr<atn::SemanticContext> pred, int alt);
virtual std::wstring toString(); virtual std::wstring toString();
private: private:

View File

@ -1,130 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
/// <summary>
/// Sometimes we need to map a key to a value but key is two pieces of data.
/// This nested hash table saves creating a single key each time we access
/// map; avoids mem creation.
/// </summary>
template<typename Key1, typename Key2, typename Value>
class DoubleKeyMap {
public:
std::map<Key1, std::map<Key2, Value>*> *data;
Value put(Key1 k1, Key2 k2, Value v) {
auto subdata = data->find(k1);
Value prev = nullptr;
std::map<Key2, Value> *data2;
if (subdata == data->end()) {
data2 = new std::map<Key2, Value>();
data->insert ( std::pair<Key1, std::map<Key2, Value>*>(k1, data2) );
} else {
data2 = subdata->second;
auto elem = data2->find(k2);
if (elem != data2->end()) {
prev = elem->second;
}
}
data2->insert ( std::pair<Key2, Value>(k2, v) );
return prev;
}
Value get(Key1 k1, Key2 k2) {
auto interior = data->find(k1);
if (interior == data->end()) {
return nullptr;
}
std::map<Key1, Value> *data2 = interior->second;
auto v = data2->find(k2);
if (v == data2->end()) {
return nullptr;
}
return v->second;
}
std::map<Key2, Value> *get(Key1 k1) {
auto data2 = data->find(k1);
if (data2 == data->end()) {
return nullptr;
}
return *data2;
}
/// <summary>
/// Get all values associated with primary key </summary>
std::set<Value> *values(Key1 k1) {
auto data2 = data->find(k1);
if (data2 == data->end()) {
return nullptr;
}
return data2->values();
}
/// <summary>
/// get all primary keys </summary>
std::set<Key1> *keySet() {
return data->keySet();
}
/// <summary>
/// get all secondary keys associated with a primary key </summary>
std::set<Key2> *keySet(Key1 k1) {
std::map<Key2, Value> *data2 = data->get(k1);
if (data2 == nullptr) {
return nullptr;
}
return data2->keySet();
}
private:
void InitializeInstanceFields() {
data = new std::map<Key1, std::map<Key2, Value>*>();
}
public:
DoubleKeyMap() {
InitializeInstanceFields();
}
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -72,14 +72,14 @@ IntervalSet IntervalSet::of(int a, int b) {
void IntervalSet::clear() { void IntervalSet::clear() {
if (_readonly) { if (_readonly) {
throw new IllegalStateException("can't alter read only IntervalSet"); throw IllegalStateException("can't alter read only IntervalSet");
} }
_intervals.clear(); _intervals.clear();
} }
void IntervalSet::add(int el) { void IntervalSet::add(int el) {
if (_readonly) { if (_readonly) {
throw new IllegalStateException("can't alter read only IntervalSet"); throw IllegalStateException("can't alter read only IntervalSet");
} }
add(el, el); add(el, el);
} }
@ -90,7 +90,7 @@ void IntervalSet::add(int a, int b) {
void IntervalSet::add(const Interval &addition) { void IntervalSet::add(const Interval &addition) {
if (_readonly) { if (_readonly) {
throw new IllegalStateException("can't alter read only IntervalSet"); throw IllegalStateException("can't alter read only IntervalSet");
} }
if (addition.b < addition.a) { if (addition.b < addition.a) {
@ -426,7 +426,7 @@ std::wstring IntervalSet::toString(const std::vector<std::wstring> &tokenNames)
} }
std::wstring IntervalSet::elementName(const std::vector<std::wstring> &tokenNames, ssize_t a) const { std::wstring IntervalSet::elementName(const std::vector<std::wstring> &tokenNames, ssize_t a) const {
if (a == Token::_EOF) { if (a == EOF) {
return L"<EOF>"; return L"<EOF>";
} else if (a == Token::EPSILON) { } else if (a == Token::EPSILON) {
return L"<EPSILON>"; return L"<EPSILON>";

View File

@ -1,138 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "StringBuilder.h"
#include "LogManager.h"
using namespace org::antlr::v4::runtime::misc;
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
LogManager::Record::Record() {
InitializeInstanceFields();
#ifdef TODO
timestamp = System::currentTimeMillis();
location = (std::exception())->getStackTrace()[0];
#endif
}
std::wstring LogManager::Record::toString() {
antlrcpp::StringBuilder *buf = new antlrcpp::StringBuilder();
#ifdef TODO
buf->append((new SimpleDateFormat(L"yyyy-MM-dd HH:mm:ss:SSS"))->format(Date(timestamp)));
buf->append(L" ");
buf->append(component);
buf->append(L" ");
buf->append(location->getFileName());
buf->append(L":");
buf->append(location->getLineNumber());
buf->append(L" ");
buf->append(msg);
#endif
return buf->toString();
}
void LogManager::Record::InitializeInstanceFields() {
timestamp = 0;
}
void LogManager::log(const std::wstring &component, const std::wstring &msg) {
Record *r = new Record();
r->component = component;
r->msg = msg;
if (records.empty()) {
records = std::vector<Record*>();
}
records.push_back(r);
}
void LogManager::log(const std::wstring &msg) {
log(L"");
}
void LogManager::save(const std::wstring &filename) {
#ifdef TODO
FileWriter *fw = new FileWriter(filename);
BufferedWriter *bw = new BufferedWriter(fw);
try {
bw->write(toString());
} finally {
bw->close();
}
#endif
}
std::wstring LogManager::save() {
#ifdef TODO
//String dir = System.getProperty("java.io.tmpdir");
std::wstring dir = L".";
std::wstring defaultFilename = dir + std::wstring(L"/antlr-") + (new SimpleDateFormat(L"yyyy-MM-dd-HH.mm.ss"))->format(Date()) + std::wstring(L".log");
save(defaultFilename);
return defaultFilename;
#else
return nullptr;
#endif
}
std::wstring LogManager::toString() {
#ifdef TODO
if (records.empty()) {
return L"";
}
std::wstring nl = System::getProperty(L"line.separator");
StringBuilder *buf = new StringBuilder();
for (auto r : records) {
buf->append(r);
buf->append(nl);
}
return buf->toString();
#else
return nullptr;
#endif
}
void LogManager::main(std::wstring args[]) {
LogManager *mgr = new LogManager();
mgr->log(L"atn", L"test msg");
mgr->log(L"dfa", L"test msg 2");
std::cout << mgr << std::endl;
mgr->save();
}
}
}
}
}
}

View File

@ -1,78 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
class LogManager {
protected:
class Record {
public:
long long timestamp;
// This is used nowhere
//StackTraceElement *location;
std::wstring component;
std::wstring msg;
Record();
virtual std::wstring toString();
private:
void InitializeInstanceFields();
};
protected:
std::vector<Record*> records;
public:
virtual void log(const std::wstring &component, const std::wstring &msg);
virtual void log(const std::wstring &msg);
virtual void save(const std::wstring &filename);
virtual std::wstring save();
virtual std::wstring toString();
static void main(std::wstring args[]);
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -1,34 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "MultiMap.h"
using namespace org::antlr::v4::runtime::misc;

View File

@ -1,116 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
#ifdef TODO
// http://stackoverflow.com/questions/2467000/is-there-a-java-map-keyset-equivalent-for-cs-stdmap
template <typename C>
class key_iterator : public std::iterator<std::bidirectional_iterator_tag,
typename C::key_type,
typename C::difference_type,
typename C::pointer,
typename C::reference> {
public:
key_iterator() { }
explicit key_iterator(typename C::const_iterator it) : it_(it) { }
typename const C::key_type& operator*() const { return it_->first; }
typename const C::key_type* operator->() const { return &it_->first; }
key_iterator& operator++() { ++it_; return *this; }
key_iterator operator++(int) { key_iterator it(*this); ++*this; return it; }
key_iterator& operator--() { --it_; return *this; }
key_iterator operator--(int) { key_iterator it(*this); --*this; return it; }
friend bool operator==(const key_iterator& lhs, const key_iterator& rhs)
{
return lhs.it_ == rhs.it_;
}
friend bool operator!=(const key_iterator& lhs, const key_iterator& rhs)
{
return !(lhs == rhs);
}
private:
typename C::const_iterator it_;
};
template <typename C>
key_iterator<C> begin_keys(const C& c) { return key_iterator<C>(c.begin()); }
template <typename C>
key_iterator<C> end_keys(const C& c) { return key_iterator<C>(c.end()); }
#endif
#ifdef TODO
This used to derive from LinkedHashMap
http://stackoverflow.com/questions/2889777/difference-between-hashmap-linkedhashmap-and-sortedmap-in-java
#endif
template<typename K, typename V>
class MultiMap : public std::map<K, std::vector<V>> {
public:
virtual void map(K key, V value) {
// std::vector<V> elementsForKey = get(key);
// if (elementsForKey.empty()) {
// elementsForKey = std::vector<V>();
// std::map<K, std::list<V>>::put(key, elementsForKey);
// }
}
virtual std::vector<std::pair<K, V>*> getPairs() {
// std::vector<std::pair<K, V>*> pairs = std::vector<std::pair<K, V>*>();
// for (K key : keySet()) {
// for (V value : get(key)) {
// pairs.push_back(new std::pair<K, V>(key, value));
// }
// }
// return pairs;
return std::vector<std::pair<K, V>*>();
}
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -72,13 +72,13 @@ namespace misc {
/// <param name="seed"> the seed for the MurmurHash algorithm </param> /// <param name="seed"> the seed for the MurmurHash algorithm </param>
/// <returns> the hash code of the data </returns> /// <returns> the hash code of the data </returns>
template<typename T> // where T is C array type template<typename T> // where T is C array type
static size_t hashCode(const T *data, std::size_t size, size_t seed) { static size_t hashCode(const std::vector<std::shared_ptr<T>> &data, size_t seed) {
size_t hash = initialize(seed); size_t hash = initialize(seed);
for (size_t i = 0; i < size; i++) { for (auto entry : data) {
hash = update(hash, (size_t)data[i]); hash = update(hash, (size_t)entry.get());
} }
return finish(hash, size); return finish(hash, data.size());
} }
}; };

View File

@ -1,34 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "OrderedHashSet.h"
using namespace org::antlr::v4::runtime::misc;

View File

@ -1,158 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
#include "Exceptions.h"
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
template <typename T>
class LinkedHashSet {
T remove(T);
bool add(T);
};
/// <summary>
/// A HashMap that remembers the order that the elements were added.
/// You can alter the ith element with set(i,value) too :) Unique list.
/// I need the replace/set-element-i functionality so I'm subclassing
/// LinkedHashSet.
/// </summary>
template<typename T>
class OrderedHashSet : public LinkedHashSet<T> {
/// <summary>
/// Track the elements as they are added to the set </summary>
protected:
//JAVA TO C++ CONVERTER NOTE: The variable elements was renamed since C++ does not allow variables with the same name as methods:
std::vector<T> elements_Renamed;
public:
virtual T get(int i) {
return elements_Renamed[i];
}
/// <summary>
/// Replace an existing value with a new value; updates the element
/// list and the hash table, but not the key as that has not changed.
/// </summary>
virtual T set(int i, T value) {
T oldElement = elements_Renamed[i];
elements_Renamed[i] = value; // update list
remove(oldElement); // now update the set: remove/add
add(value);
return oldElement;
}
virtual bool remove(int i) {
T o = elements_Renamed.remove(i);
return remove(o);
}
/// <summary>
/// Add a value to list; keep in hashtable for consistency also;
/// Key is object itself. Good for say asking if a certain string is in
/// a list of strings.
/// </summary>
virtual bool add(T value) override {
bool result = add(value);
if (result) { // only track if new element not in set
elements_Renamed.push_back(value);
}
return result;
}
virtual bool remove(void *o) override {
throw new UnsupportedOperationException();
}
virtual void clear() override {
elements_Renamed.clear();
LinkedHashSet<T>::clear();
}
virtual size_t hashCode() override {
return elements_Renamed.hashCode();
}
virtual bool equals(void *o) override {
if (!(dynamic_cast<OrderedHashSet<T>*>(o) != nullptr)) {
return false;
}
// System.out.print("equals " + this + ", " + o+" = ");
bool same = elements_Renamed.size() > 0 && elements_Renamed.equals((static_cast<OrderedHashSet<T>*>(o))->elements_Renamed);
// System.out.println(same);
return same;
}
#ifdef TODO
virtual std::iterator<T> *iterator() override {
return elements_Renamed.begin();
}
#endif
/// <summary>
/// Return the List holding list of table elements. Note that you are
/// NOT getting a copy so don't write to the list.
/// </summary>
virtual std::vector<T> elements() {
return elements_Renamed;
}
virtual void *clone() override { // safe (result of clone)
OrderedHashSet<T> *dup = static_cast<OrderedHashSet<T>*>(LinkedHashSet<T>::clone());
dup->elements_Renamed = std::vector<T>(this->elements_Renamed);
return dup;
}
virtual std::wstring toString() override {
return elements_Renamed.toString();
}
private:
void InitializeInstanceFields() {
elements_Renamed = std::vector<T>();
}
public:
OrderedHashSet() {
InitializeInstanceFields();
}
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -1,52 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "ParseCancellationException.h"
using namespace org::antlr::v4::runtime::misc;
ParseCancellationException::ParseCancellationException() {
}
ParseCancellationException::ParseCancellationException(const std::wstring &message) {
}
ParseCancellationException::ParseCancellationException(std::exception cause) {
#ifdef TODO
initCause(cause);
#endif
}
ParseCancellationException::ParseCancellationException(const std::wstring &message, std::exception cause) {
#ifdef TODO
initCause(cause);
#endif
}

View File

@ -1,65 +0,0 @@
/*
* [The "BSD license"]
* Copyright (c) 2016 Mike Lischke
* Copyright (c) 2013 Terence Parr
* Copyright (c) 2013 Dan McLaughlin
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
namespace org {
namespace antlr {
namespace v4 {
namespace runtime {
namespace misc {
/// <summary>
/// This exception is thrown to cancel a parsing operation. This exception does
/// not extend <seealso cref="RecognitionException"/>, allowing it to bypass the standard
/// error recovery mechanisms. <seealso cref="BailErrorStrategy"/> throws this exception in
/// response to a parse error.
///
/// @author Sam Harwell
/// </summary>
class ParseCancellationException : public std::exception {
public:
ParseCancellationException();
ParseCancellationException(const std::wstring &message);
ParseCancellationException(std::exception cause);
ParseCancellationException(const std::wstring &message, std::exception cause);
};
} // namespace atn
} // namespace runtime
} // namespace v4
} // namespace antlr
} // namespace org

View File

@ -47,3 +47,17 @@ std::wstring Arrays::listToString(const std::vector<std::wstring> &list, const s
return sb.toString(); return sb.toString();
} }
template <>
std::wstring Arrays::toString(const std::vector<org::antlr::v4::runtime::tree::Tree*> &source) {
std::wstring result = L"[";
bool firstEntry = true;
for (auto value : source) {
result += value->toStringTree();
if (firstEntry) {
result += L", ";
firstEntry = false;
}
}
return result + L"]";
}

View File

@ -31,6 +31,7 @@
#pragma once #pragma once
#include "StringBuilder.h" #include "StringBuilder.h"
#include "Tree.h"
namespace antlrcpp { namespace antlrcpp {
@ -57,7 +58,19 @@ namespace antlrcpp {
return false; return false;
for (size_t i = 0; i < a.size(); ++i) for (size_t i = 0; i < a.size(); ++i)
if (*a[i] != *b[i]) // Requires that the != operator is supported by the template type. if (*a[i] != *b[i])
return false;
return true;
}
template <typename T>
static bool equals(const std::vector<std::weak_ptr<T>> &a, const std::vector<std::weak_ptr<T>> &b) {
if (a.size() != b.size())
return false;
for (size_t i = 0; i < a.size(); ++i)
if (*a[i].lock() != *b[i].lock())
return false; return false;
return true; return true;
@ -71,6 +84,50 @@ namespace antlrcpp {
return result; return result;
} }
template <typename T>
static std::wstring toString(const std::vector<T> &source) {
std::wstring result = L"[";
bool firstEntry = true;
for (auto &value : source) {
result += value.toString();
if (firstEntry) {
result += L", ";
firstEntry = false;
}
}
return result + L"]";
}
template <typename T>
static std::wstring toString(const std::vector<std::shared_ptr<T>> &source) {
std::wstring result = L"[";
bool firstEntry = true;
for (auto &value : source) {
result += value->toString();
if (firstEntry) {
result += L", ";
firstEntry = false;
}
}
return result + L"]";
}
template <typename T>
static std::wstring toString(const std::vector<T*> &source) {
std::wstring result = L"[";
bool firstEntry = true;
for (auto value : source) {
result += value->toString();
if (firstEntry) {
result += L", ";
firstEntry = false;
}
}
return result + L"]";
}
}; };
template <>
std::wstring Arrays::toString(const std::vector<org::antlr::v4::runtime::tree::Tree*> &source);
} }

View File

@ -53,5 +53,45 @@ namespace antlrcpp {
template <typename F> template <typename F>
FinalAction<F> finally(F f) { return FinalAction<F>(f); } FinalAction<F> finally(F f) { return FinalAction<F>(f); }
// Convenience functions to avoid lengthy dynamic_cast() != nullptr checks in many places.
template <typename T1, typename T2>
bool is(T2 obj) { // For value types.
return dynamic_cast<T1 *>(&obj) != nullptr;
}
template <typename T1, typename T2>
bool is(T2 *obj) { // For pointer types.
return dynamic_cast<T1>(obj) != nullptr;
}
template <typename T1, typename T2>
bool is(std::shared_ptr<T2> obj) { // For shared pointers.
return dynamic_cast<T1*>(obj.get()) != nullptr;
}
} // namespace antlrcpp } // namespace antlrcpp
namespace std {
// Comparing weak and shared pointers.
template <typename T>
bool operator == (const std::weak_ptr<T> &lhs, const std::weak_ptr<T> &rhs) {
if (lhs.expired() && rhs.expired())
return true;
if (lhs.expired() || rhs.expired())
return false;
return (lhs.lock() == rhs.lock());
}
template <typename T>
bool operator == (const std::shared_ptr<T> &lhs, const std::shared_ptr<T> &rhs) {
if (!lhs && !rhs)
return true;
if (!lhs || !rhs)
return false;
return (*lhs == *rhs);
}
} // namespace std

View File

@ -93,18 +93,13 @@ namespace org {
namespace misc { namespace misc {
template<typename T> class AbstractEqualityComparator; template<typename T> class AbstractEqualityComparator;
template<typename T> class Array2DHashSet;
template<typename Key1, typename Key2, typename Value> class DoubleKeyMap;
template<typename T> class EqualityComparator; template<typename T> class EqualityComparator;
class Interval; class Interval;
class IntervalSet; class IntervalSet;
class JFileChooserConfirmOverwrite; class JFileChooserConfirmOverwrite;
class LogManager;
template<typename K, typename V> class MultiMap;
class MurmurHash; class MurmurHash;
class ObjectEqualityComparator; class ObjectEqualityComparator;
template<typename T> class OrderedHashSet;
class ParseCancellationException; class ParseCancellationException;
class TestRig; class TestRig;
class Utils; class Utils;
@ -143,17 +138,16 @@ namespace org {
class PlusLoopbackState; class PlusLoopbackState;
class PrecedencePredicateTransition; class PrecedencePredicateTransition;
class PredicateTransition; class PredicateTransition;
class PredictionContext; class PredictionContext; typedef std::shared_ptr<PredictionContext> PredictionContextRef;
class PredictionContextCache;
enum class PredictionMode; enum class PredictionMode;
class PredictionModeClass; class PredictionModeClass;
class RangeTransition; class RangeTransition;
class RuleStartState; class RuleStartState;
class RuleStopState; class RuleStopState;
class RuleTransition; class RuleTransition;
class SemanticContext; class SemanticContext; typedef std::shared_ptr<SemanticContext> SemanticContextRef;
class SetTransition; class SetTransition;
class SingletonPredictionContext; class SingletonPredictionContext; typedef std::shared_ptr<SingletonPredictionContext> SingletonPredictionContextRef;
class StarBlockStartState; class StarBlockStartState;
class StarLoopEntryState; class StarLoopEntryState;
class StarLoopbackState; class StarLoopbackState;
@ -194,18 +188,6 @@ namespace org {
class TokenTagToken; class TokenTagToken;
} }
namespace xpath {
class XPath;
class XPathElement;
class XPathLexerErrorListener;
class XPathRuleAnywhereElement;
class XPathRuleElement;
class XPathTokenAnywhereElement;
class XPathTokenElement;
class XPathWildcardAnywhereElement;
class XPathWildcardElement;
}
} }
} }
} }

Some files were not shown because too many files have changed in this diff Show More