1 /* Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
2  * Use of this file is governed by the BSD 3-clause license that
3  * can be found in the LICENSE.txt file in the project root.
4  */
5 
6 #include "atn/ATNDeserializationOptions.h"
7 
8 #include "atn/ATNType.h"
9 #include "atn/ATNState.h"
10 #include "atn/ATN.h"
11 
12 #include "atn/LoopEndState.h"
13 #include "atn/DecisionState.h"
14 #include "atn/RuleStartState.h"
15 #include "atn/RuleStopState.h"
16 #include "atn/TokensStartState.h"
17 #include "atn/RuleTransition.h"
18 #include "atn/EpsilonTransition.h"
19 #include "atn/PlusLoopbackState.h"
20 #include "atn/PlusBlockStartState.h"
21 #include "atn/StarLoopbackState.h"
22 #include "atn/BasicBlockStartState.h"
23 #include "atn/BasicState.h"
24 #include "atn/BlockEndState.h"
25 #include "atn/StarLoopEntryState.h"
26 
27 #include "atn/AtomTransition.h"
28 #include "atn/StarBlockStartState.h"
29 #include "atn/RangeTransition.h"
30 #include "atn/PredicateTransition.h"
31 #include "atn/PrecedencePredicateTransition.h"
32 #include "atn/ActionTransition.h"
33 #include "atn/SetTransition.h"
34 #include "atn/NotSetTransition.h"
35 #include "atn/WildcardTransition.h"
36 #include "Token.h"
37 
38 #include "misc/IntervalSet.h"
39 #include "Exceptions.h"
40 #include "support/CPPUtils.h"
41 #include "support/StringUtils.h"
42 
43 #include "atn/LexerCustomAction.h"
44 #include "atn/LexerChannelAction.h"
45 #include "atn/LexerModeAction.h"
46 #include "atn/LexerMoreAction.h"
47 #include "atn/LexerPopModeAction.h"
48 #include "atn/LexerPushModeAction.h"
49 #include "atn/LexerSkipAction.h"
50 #include "atn/LexerTypeAction.h"
51 
52 #include "atn/ATNDeserializer.h"
53 
54 #include <string>
55 
56 using namespace antlr4;
57 using namespace antlr4::atn;
58 using namespace antlrcpp;
59 
60 namespace {
61 
deserializeInt32(const std::vector<uint16_t> & data,size_t offset)62 uint32_t deserializeInt32(const std::vector<uint16_t>& data, size_t offset) {
63   return (uint32_t)data[offset] | ((uint32_t)data[offset + 1] << 16);
64 }
65 
readUnicodeInt(const std::vector<uint16_t> & data,int & p)66 ssize_t readUnicodeInt(const std::vector<uint16_t>& data, int& p) {
67   return static_cast<ssize_t>(data[p++]);
68 }
69 
readUnicodeInt32(const std::vector<uint16_t> & data,int & p)70 ssize_t readUnicodeInt32(const std::vector<uint16_t>& data, int& p) {
71   auto result = deserializeInt32(data, p);
72   p += 2;
73   return static_cast<ssize_t>(result);
74 }
75 
76 // We templatize this on the function type so the optimizer can inline
77 // the 16- or 32-bit readUnicodeInt/readUnicodeInt32 as needed.
78 template <typename F>
deserializeSets(const std::vector<uint16_t> & data,int & p,std::vector<misc::IntervalSet> & sets,F readUnicode)79 void deserializeSets(
80   const std::vector<uint16_t>& data,
81   int& p,
82   std::vector<misc::IntervalSet>& sets,
83   F readUnicode) {
84   int nsets = data[p++];
85   for (int i = 0; i < nsets; i++) {
86     int nintervals = data[p++];
87     misc::IntervalSet set;
88 
89     bool containsEof = data[p++] != 0;
90     if (containsEof) {
91       set.add(-1);
92     }
93 
94     for (int j = 0; j < nintervals; j++) {
95       auto a = readUnicode(data, p);
96       auto b = readUnicode(data, p);
97       set.add(a, b);
98     }
99     sets.push_back(set);
100   }
101 }
102 
103 }
104 
ATNDeserializer()105 ATNDeserializer::ATNDeserializer(): ATNDeserializer(ATNDeserializationOptions::getDefaultOptions()) {
106 }
107 
ATNDeserializer(const ATNDeserializationOptions & dso)108 ATNDeserializer::ATNDeserializer(const ATNDeserializationOptions& dso): deserializationOptions(dso) {
109 }
110 
~ATNDeserializer()111 ATNDeserializer::~ATNDeserializer() {
112 }
113 
114 /**
115  * This value should never change. Updates following this version are
116  * reflected as change in the unique ID SERIALIZED_UUID.
117  */
ADDED_PRECEDENCE_TRANSITIONS()118 antlrcpp::Guid ATNDeserializer::ADDED_PRECEDENCE_TRANSITIONS() {
119   return antlrcpp::Guid("1DA0C57D-6C06-438A-9B27-10BCB3CE0F61");
120 }
121 
ADDED_LEXER_ACTIONS()122 antlrcpp::Guid ATNDeserializer::ADDED_LEXER_ACTIONS() {
123   return antlrcpp::Guid("AADB8D7E-AEEF-4415-AD2B-8204D6CF042E");
124 }
125 
ADDED_UNICODE_SMP()126 antlrcpp::Guid ATNDeserializer::ADDED_UNICODE_SMP() {
127   return antlrcpp::Guid("59627784-3BE5-417A-B9EB-8131A7286089");
128 }
129 
SERIALIZED_UUID()130 antlrcpp::Guid ATNDeserializer::SERIALIZED_UUID() {
131   return ADDED_UNICODE_SMP();
132 }
133 
BASE_SERIALIZED_UUID()134 antlrcpp::Guid ATNDeserializer::BASE_SERIALIZED_UUID() {
135   return antlrcpp::Guid("33761B2D-78BB-4A43-8B0B-4F5BEE8AACF3");
136 }
137 
SUPPORTED_UUIDS()138 std::vector<antlrcpp::Guid>& ATNDeserializer::SUPPORTED_UUIDS() {
139   static std::vector<antlrcpp::Guid> singleton = { BASE_SERIALIZED_UUID(), ADDED_PRECEDENCE_TRANSITIONS(), ADDED_LEXER_ACTIONS(), ADDED_UNICODE_SMP() };
140   return singleton;
141 }
142 
isFeatureSupported(const antlrcpp::Guid & feature,const antlrcpp::Guid & actualUuid)143 bool ATNDeserializer::isFeatureSupported(const antlrcpp::Guid &feature, const antlrcpp::Guid &actualUuid) {
144   auto featureIterator = std::find(SUPPORTED_UUIDS().begin(), SUPPORTED_UUIDS().end(), feature);
145   if (featureIterator == SUPPORTED_UUIDS().end()) {
146     return false;
147   }
148   auto actualIterator = std::find(SUPPORTED_UUIDS().begin(), SUPPORTED_UUIDS().end(), actualUuid);
149   if (actualIterator == SUPPORTED_UUIDS().end()) {
150     return false;
151   }
152 
153   return std::distance(featureIterator, actualIterator) >= 0;
154 }
155 
deserialize(const std::vector<uint16_t> & input)156 ATN ATNDeserializer::deserialize(const std::vector<uint16_t>& input) {
157   // Don't adjust the first value since that's the version number.
158   std::vector<uint16_t> data(input.size());
159   data[0] = input[0];
160   for (size_t i = 1; i < input.size(); ++i) {
161     data[i] = input[i] - 2;
162   }
163 
164   int p = 0;
165   int version = data[p++];
166   if (version != SERIALIZED_VERSION) {
167     std::string reason = "Could not deserialize ATN with version" + std::to_string(version) + "(expected " + std::to_string(SERIALIZED_VERSION) + ").";
168 
169     throw UnsupportedOperationException(reason);
170   }
171 
172   antlrcpp::Guid uuid = toUUID(data.data(), p);
173   p += 8;
174   auto uuidIterator = std::find(SUPPORTED_UUIDS().begin(), SUPPORTED_UUIDS().end(), uuid);
175   if (uuidIterator == SUPPORTED_UUIDS().end()) {
176     std::string reason = "Could not deserialize ATN with UUID " + uuid.toString() + " (expected " +
177       SERIALIZED_UUID().toString() + " or a legacy UUID).";
178 
179     throw UnsupportedOperationException(reason);
180   }
181 
182   bool supportsPrecedencePredicates = isFeatureSupported(ADDED_PRECEDENCE_TRANSITIONS(), uuid);
183   bool supportsLexerActions = isFeatureSupported(ADDED_LEXER_ACTIONS(), uuid);
184 
185   ATNType grammarType = (ATNType)data[p++];
186   size_t maxTokenType = data[p++];
187   ATN atn(grammarType, maxTokenType);
188 
189   //
190   // STATES
191   //
192   std::vector<std::pair<LoopEndState*, size_t>> loopBackStateNumbers;
193   std::vector<std::pair<BlockStartState*, size_t>> endStateNumbers;
194   size_t nstates = data[p++];
195   for (size_t i = 0; i < nstates; i++) {
196     size_t stype = data[p++];
197     // ignore bad type of states
198     if (stype == ATNState::ATN_INVALID_TYPE) {
199       atn.addState(nullptr);
200       continue;
201     }
202 
203     size_t ruleIndex = data[p++];
204     if (ruleIndex == 0xFFFF) {
205       ruleIndex = INVALID_INDEX;
206     }
207 
208     ATNState *s = stateFactory(stype, ruleIndex);
209     if (stype == ATNState::LOOP_END) { // special case
210       int loopBackStateNumber = data[p++];
211       loopBackStateNumbers.push_back({ (LoopEndState*)s,  loopBackStateNumber });
212     } else if (is<BlockStartState*>(s)) {
213       int endStateNumber = data[p++];
214       endStateNumbers.push_back({ (BlockStartState*)s, endStateNumber });
215     }
216     atn.addState(s);
217   }
218 
219   // delay the assignment of loop back and end states until we know all the state instances have been initialized
220   for (auto &pair : loopBackStateNumbers) {
221     pair.first->loopBackState = atn.states[pair.second];
222   }
223 
224   for (auto &pair : endStateNumbers) {
225     pair.first->endState = (BlockEndState*)atn.states[pair.second];
226   }
227 
228   size_t numNonGreedyStates = data[p++];
229   for (size_t i = 0; i < numNonGreedyStates; i++) {
230     size_t stateNumber = data[p++];
231     // The serialized ATN must be specifying the right states, so that the
232     // cast below is correct.
233     ((DecisionState *)atn.states[stateNumber])->nonGreedy = true;
234   }
235 
236   if (supportsPrecedencePredicates) {
237     size_t numPrecedenceStates = data[p++];
238     for (size_t i = 0; i < numPrecedenceStates; i++) {
239       size_t stateNumber = data[p++];
240       ((RuleStartState *)atn.states[stateNumber])->isLeftRecursiveRule = true;
241     }
242   }
243 
244   //
245   // RULES
246   //
247   size_t nrules = data[p++];
248   for (size_t i = 0; i < nrules; i++) {
249     size_t s = data[p++];
250     // Also here, the serialized atn must ensure to point to the correct class type.
251     RuleStartState *startState = (RuleStartState*)atn.states[s];
252     atn.ruleToStartState.push_back(startState);
253     if (atn.grammarType == ATNType::LEXER) {
254       size_t tokenType = data[p++];
255       if (tokenType == 0xFFFF) {
256         tokenType = Token::EOF;
257       }
258 
259       atn.ruleToTokenType.push_back(tokenType);
260 
261       if (!isFeatureSupported(ADDED_LEXER_ACTIONS(), uuid)) {
262         // this piece of unused metadata was serialized prior to the
263         // addition of LexerAction
264         //int actionIndexIgnored = data[p++];
265         p++;
266       }
267     }
268   }
269 
270   atn.ruleToStopState.resize(nrules);
271   for (ATNState *state : atn.states) {
272     if (!is<RuleStopState*>(state)) {
273       continue;
274     }
275 
276     RuleStopState *stopState = static_cast<RuleStopState*>(state);
277     atn.ruleToStopState[state->ruleIndex] = stopState;
278     atn.ruleToStartState[state->ruleIndex]->stopState = stopState;
279   }
280 
281   //
282   // MODES
283   //
284   size_t nmodes = data[p++];
285   for (size_t i = 0; i < nmodes; i++) {
286     size_t s = data[p++];
287     atn.modeToStartState.push_back(static_cast<TokensStartState*>(atn.states[s]));
288   }
289 
290   //
291   // SETS
292   //
293   std::vector<misc::IntervalSet> sets;
294 
295   // First, deserialize sets with 16-bit arguments <= U+FFFF.
296   deserializeSets(data, p, sets, readUnicodeInt);
297 
298   // Next, if the ATN was serialized with the Unicode SMP feature,
299   // deserialize sets with 32-bit arguments <= U+10FFFF.
300   if (isFeatureSupported(ADDED_UNICODE_SMP(), uuid)) {
301     deserializeSets(data, p, sets, readUnicodeInt32);
302   }
303 
304   //
305   // EDGES
306   //
307   int nedges = data[p++];
308   for (int i = 0; i < nedges; i++) {
309     size_t src = data[p];
310     size_t trg = data[p + 1];
311     size_t ttype = data[p + 2];
312     size_t arg1 = data[p + 3];
313     size_t arg2 = data[p + 4];
314     size_t arg3 = data[p + 5];
315     Transition *trans = edgeFactory(atn, ttype, src, trg, arg1, arg2, arg3, sets);
316     ATNState *srcState = atn.states[src];
317     srcState->addTransition(trans);
318     p += 6;
319   }
320 
321   // edges for rule stop states can be derived, so they aren't serialized
322   for (ATNState *state : atn.states) {
323     for (size_t i = 0; i < state->transitions.size(); i++) {
324       Transition *t = state->transitions[i];
325       if (!is<RuleTransition*>(t)) {
326         continue;
327       }
328 
329       RuleTransition *ruleTransition = static_cast<RuleTransition*>(t);
330       size_t outermostPrecedenceReturn = INVALID_INDEX;
331       if (atn.ruleToStartState[ruleTransition->target->ruleIndex]->isLeftRecursiveRule) {
332         if (ruleTransition->precedence == 0) {
333           outermostPrecedenceReturn = ruleTransition->target->ruleIndex;
334         }
335       }
336 
337       EpsilonTransition *returnTransition = new EpsilonTransition(ruleTransition->followState, outermostPrecedenceReturn); /* mem check: freed in ANTState d-tor */
338       atn.ruleToStopState[ruleTransition->target->ruleIndex]->addTransition(returnTransition);
339     }
340   }
341 
342   for (ATNState *state : atn.states) {
343     if (is<BlockStartState *>(state)) {
344       BlockStartState *startState = static_cast<BlockStartState *>(state);
345 
346       // we need to know the end state to set its start state
347       if (startState->endState == nullptr) {
348         throw IllegalStateException();
349       }
350 
351       // block end states can only be associated to a single block start state
352       if (startState->endState->startState != nullptr) {
353         throw IllegalStateException();
354       }
355 
356       startState->endState->startState = static_cast<BlockStartState*>(state);
357     }
358 
359     if (is<PlusLoopbackState*>(state)) {
360       PlusLoopbackState *loopbackState = static_cast<PlusLoopbackState *>(state);
361       for (size_t i = 0; i < loopbackState->transitions.size(); i++) {
362         ATNState *target = loopbackState->transitions[i]->target;
363         if (is<PlusBlockStartState *>(target)) {
364           (static_cast<PlusBlockStartState *>(target))->loopBackState = loopbackState;
365         }
366       }
367     } else if (is<StarLoopbackState *>(state)) {
368       StarLoopbackState *loopbackState = static_cast<StarLoopbackState *>(state);
369       for (size_t i = 0; i < loopbackState->transitions.size(); i++) {
370         ATNState *target = loopbackState->transitions[i]->target;
371         if (is<StarLoopEntryState *>(target)) {
372           (static_cast<StarLoopEntryState*>(target))->loopBackState = loopbackState;
373         }
374       }
375     }
376   }
377 
378   //
379   // DECISIONS
380   //
381   size_t ndecisions = data[p++];
382   for (size_t i = 1; i <= ndecisions; i++) {
383     size_t s = data[p++];
384     DecisionState *decState = dynamic_cast<DecisionState*>(atn.states[s]);
385     if (decState == nullptr)
386       throw IllegalStateException();
387 
388     atn.decisionToState.push_back(decState);
389     decState->decision = (int)i - 1;
390   }
391 
392   //
393   // LEXER ACTIONS
394   //
395   if (atn.grammarType == ATNType::LEXER) {
396     if (supportsLexerActions) {
397       atn.lexerActions.resize(data[p++]);
398       for (size_t i = 0; i < atn.lexerActions.size(); i++) {
399         LexerActionType actionType = (LexerActionType)data[p++];
400         int data1 = data[p++];
401         if (data1 == 0xFFFF) {
402           data1 = -1;
403         }
404 
405         int data2 = data[p++];
406         if (data2 == 0xFFFF) {
407           data2 = -1;
408         }
409 
410         atn.lexerActions[i] = lexerActionFactory(actionType, data1, data2);
411       }
412     } else {
413       // for compatibility with older serialized ATNs, convert the old
414       // serialized action index for action transitions to the new
415       // form, which is the index of a LexerCustomAction
416       for (ATNState *state : atn.states) {
417         for (size_t i = 0; i < state->transitions.size(); i++) {
418           Transition *transition = state->transitions[i];
419           if (!is<ActionTransition *>(transition)) {
420             continue;
421           }
422 
423           size_t ruleIndex = static_cast<ActionTransition *>(transition)->ruleIndex;
424           size_t actionIndex = static_cast<ActionTransition *>(transition)->actionIndex;
425           Ref<LexerCustomAction> lexerAction = std::make_shared<LexerCustomAction>(ruleIndex, actionIndex);
426           state->transitions[i] = new ActionTransition(transition->target, ruleIndex, atn.lexerActions.size(), false); /* mem-check freed in ATNState d-tor */
427           delete transition; // ml: no longer needed since we just replaced it.
428           atn.lexerActions.push_back(lexerAction);
429         }
430       }
431     }
432   }
433 
434   markPrecedenceDecisions(atn);
435 
436   if (deserializationOptions.isVerifyATN()) {
437     verifyATN(atn);
438   }
439 
440   if (deserializationOptions.isGenerateRuleBypassTransitions() && atn.grammarType == ATNType::PARSER) {
441     atn.ruleToTokenType.resize(atn.ruleToStartState.size());
442     for (size_t i = 0; i < atn.ruleToStartState.size(); i++) {
443       atn.ruleToTokenType[i] = int(atn.maxTokenType + i + 1);
444     }
445 
446     for (std::vector<RuleStartState*>::size_type i = 0; i < atn.ruleToStartState.size(); i++) {
447       BasicBlockStartState *bypassStart = new BasicBlockStartState(); /* mem check: freed in ATN d-tor */
448       bypassStart->ruleIndex = (int)i;
449       atn.addState(bypassStart);
450 
451       BlockEndState *bypassStop = new BlockEndState(); /* mem check: freed in ATN d-tor */
452       bypassStop->ruleIndex = (int)i;
453       atn.addState(bypassStop);
454 
455       bypassStart->endState = bypassStop;
456       atn.defineDecisionState(bypassStart);
457 
458       bypassStop->startState = bypassStart;
459 
460       ATNState *endState;
461       Transition *excludeTransition = nullptr;
462       if (atn.ruleToStartState[i]->isLeftRecursiveRule) {
463         // wrap from the beginning of the rule to the StarLoopEntryState
464         endState = nullptr;
465         for (ATNState *state : atn.states) {
466           if (state->ruleIndex != i) {
467             continue;
468           }
469 
470           if (!is<StarLoopEntryState*>(state)) {
471             continue;
472           }
473 
474           ATNState *maybeLoopEndState = state->transitions[state->transitions.size() - 1]->target;
475           if (!is<LoopEndState*>(maybeLoopEndState)) {
476             continue;
477           }
478 
479           if (maybeLoopEndState->epsilonOnlyTransitions && is<RuleStopState*>(maybeLoopEndState->transitions[0]->target)) {
480             endState = state;
481             break;
482           }
483         }
484 
485         if (endState == nullptr) {
486           throw UnsupportedOperationException("Couldn't identify final state of the precedence rule prefix section.");
487 
488         }
489 
490         excludeTransition = (static_cast<StarLoopEntryState*>(endState))->loopBackState->transitions[0];
491       } else {
492         endState = atn.ruleToStopState[i];
493       }
494 
495       // all non-excluded transitions that currently target end state need to target blockEnd instead
496       for (ATNState *state : atn.states) {
497         for (Transition *transition : state->transitions) {
498           if (transition == excludeTransition) {
499             continue;
500           }
501 
502           if (transition->target == endState) {
503             transition->target = bypassStop;
504           }
505         }
506       }
507 
508       // all transitions leaving the rule start state need to leave blockStart instead
509       while (atn.ruleToStartState[i]->transitions.size() > 0) {
510         Transition *transition = atn.ruleToStartState[i]->removeTransition(atn.ruleToStartState[i]->transitions.size() - 1);
511         bypassStart->addTransition(transition);
512       }
513 
514       // link the new states
515       atn.ruleToStartState[i]->addTransition(new EpsilonTransition(bypassStart));  /* mem check: freed in ATNState d-tor */
516       bypassStop->addTransition(new EpsilonTransition(endState)); /* mem check: freed in ATNState d-tor */
517 
518       ATNState *matchState = new BasicState(); /* mem check: freed in ATN d-tor */
519       atn.addState(matchState);
520       matchState->addTransition(new AtomTransition(bypassStop, atn.ruleToTokenType[i])); /* mem check: freed in ATNState d-tor */
521       bypassStart->addTransition(new EpsilonTransition(matchState)); /* mem check: freed in ATNState d-tor */
522     }
523 
524     if (deserializationOptions.isVerifyATN()) {
525       // reverify after modification
526       verifyATN(atn);
527     }
528   }
529 
530   return atn;
531 }
532 
533 /**
534  * Analyze the {@link StarLoopEntryState} states in the specified ATN to set
535  * the {@link StarLoopEntryState#isPrecedenceDecision} field to the
536  * correct value.
537  *
538  * @param atn The ATN.
539  */
markPrecedenceDecisions(const ATN & atn)540 void ATNDeserializer::markPrecedenceDecisions(const ATN &atn) {
541   for (ATNState *state : atn.states) {
542     if (!is<StarLoopEntryState *>(state)) {
543       continue;
544     }
545 
546     /* We analyze the ATN to determine if this ATN decision state is the
547      * decision for the closure block that determines whether a
548      * precedence rule should continue or complete.
549      */
550     if (atn.ruleToStartState[state->ruleIndex]->isLeftRecursiveRule) {
551       ATNState *maybeLoopEndState = state->transitions[state->transitions.size() - 1]->target;
552       if (is<LoopEndState *>(maybeLoopEndState)) {
553         if (maybeLoopEndState->epsilonOnlyTransitions && is<RuleStopState *>(maybeLoopEndState->transitions[0]->target)) {
554           static_cast<StarLoopEntryState *>(state)->isPrecedenceDecision = true;
555         }
556       }
557     }
558   }
559 }
560 
verifyATN(const ATN & atn)561 void ATNDeserializer::verifyATN(const ATN &atn) {
562   // verify assumptions
563   for (ATNState *state : atn.states) {
564     if (state == nullptr) {
565       continue;
566     }
567 
568     checkCondition(state->epsilonOnlyTransitions || state->transitions.size() <= 1);
569 
570     if (is<PlusBlockStartState *>(state)) {
571       checkCondition((static_cast<PlusBlockStartState *>(state))->loopBackState != nullptr);
572     }
573 
574     if (is<StarLoopEntryState *>(state)) {
575       StarLoopEntryState *starLoopEntryState = static_cast<StarLoopEntryState*>(state);
576       checkCondition(starLoopEntryState->loopBackState != nullptr);
577       checkCondition(starLoopEntryState->transitions.size() == 2);
578 
579       if (is<StarBlockStartState *>(starLoopEntryState->transitions[0]->target)) {
580         checkCondition(static_cast<LoopEndState *>(starLoopEntryState->transitions[1]->target) != nullptr);
581         checkCondition(!starLoopEntryState->nonGreedy);
582       } else if (is<LoopEndState *>(starLoopEntryState->transitions[0]->target)) {
583         checkCondition(is<StarBlockStartState *>(starLoopEntryState->transitions[1]->target));
584         checkCondition(starLoopEntryState->nonGreedy);
585       } else {
586         throw IllegalStateException();
587 
588       }
589     }
590 
591     if (is<StarLoopbackState *>(state)) {
592       checkCondition(state->transitions.size() == 1);
593       checkCondition(is<StarLoopEntryState *>(state->transitions[0]->target));
594     }
595 
596     if (is<LoopEndState *>(state)) {
597       checkCondition((static_cast<LoopEndState *>(state))->loopBackState != nullptr);
598     }
599 
600     if (is<RuleStartState *>(state)) {
601       checkCondition((static_cast<RuleStartState *>(state))->stopState != nullptr);
602     }
603 
604     if (is<BlockStartState *>(state)) {
605       checkCondition((static_cast<BlockStartState *>(state))->endState != nullptr);
606     }
607 
608     if (is<BlockEndState *>(state)) {
609       checkCondition((static_cast<BlockEndState *>(state))->startState != nullptr);
610     }
611 
612     if (is<DecisionState *>(state)) {
613       DecisionState *decisionState = static_cast<DecisionState *>(state);
614       checkCondition(decisionState->transitions.size() <= 1 || decisionState->decision >= 0);
615     } else {
616       checkCondition(state->transitions.size() <= 1 || is<RuleStopState *>(state));
617     }
618   }
619 }
620 
checkCondition(bool condition)621 void ATNDeserializer::checkCondition(bool condition) {
622   checkCondition(condition, "");
623 }
624 
checkCondition(bool condition,const std::string & message)625 void ATNDeserializer::checkCondition(bool condition, const std::string &message) {
626   if (!condition) {
627     throw IllegalStateException(message);
628   }
629 }
630 
toUUID(const unsigned short * data,size_t offset)631 antlrcpp::Guid ATNDeserializer::toUUID(const unsigned short *data, size_t offset) {
632   return antlrcpp::Guid((uint16_t *)data + offset, true);
633 }
634 
635 /* mem check: all created instances are freed in the d-tor of the ATNState they are added to. */
edgeFactory(const ATN & atn,size_t type,size_t,size_t trg,size_t arg1,size_t arg2,size_t arg3,const std::vector<misc::IntervalSet> & sets)636 Transition *ATNDeserializer::edgeFactory(const ATN &atn, size_t type, size_t /*src*/, size_t trg, size_t arg1,
637                                          size_t arg2, size_t arg3,
638   const std::vector<misc::IntervalSet> &sets) {
639 
640   ATNState *target = atn.states[trg];
641   switch (type) {
642     case Transition::EPSILON:
643       return new EpsilonTransition(target);
644     case Transition::RANGE:
645       if (arg3 != 0) {
646         return new RangeTransition(target, Token::EOF, arg2);
647       } else {
648         return new RangeTransition(target, arg1, arg2);
649       }
650     case Transition::RULE:
651       return new RuleTransition(static_cast<RuleStartState*>(atn.states[arg1]), arg2, (int)arg3, target);
652     case Transition::PREDICATE:
653       return new PredicateTransition(target, arg1, arg2, arg3 != 0);
654     case Transition::PRECEDENCE:
655       return new PrecedencePredicateTransition(target, (int)arg1);
656     case Transition::ATOM:
657       if (arg3 != 0) {
658         return new AtomTransition(target, Token::EOF);
659       } else {
660         return new AtomTransition(target, arg1);
661       }
662     case Transition::ACTION:
663       return new ActionTransition(target, arg1, arg2, arg3 != 0);
664     case Transition::SET:
665       return new SetTransition(target, sets[arg1]);
666     case Transition::NOT_SET:
667       return new NotSetTransition(target, sets[arg1]);
668     case Transition::WILDCARD:
669       return new WildcardTransition(target);
670   }
671 
672   throw IllegalArgumentException("The specified transition type is not valid.");
673 }
674 
675 /* mem check: all created instances are freed in the d-tor of the ATN. */
stateFactory(size_t type,size_t ruleIndex)676 ATNState* ATNDeserializer::stateFactory(size_t type, size_t ruleIndex) {
677   ATNState *s;
678   switch (type) {
679     case ATNState::ATN_INVALID_TYPE:
680       return nullptr;
681     case ATNState::BASIC :
682       s = new BasicState();
683       break;
684     case ATNState::RULE_START :
685       s = new RuleStartState();
686       break;
687     case ATNState::BLOCK_START :
688       s = new BasicBlockStartState();
689       break;
690     case ATNState::PLUS_BLOCK_START :
691       s = new PlusBlockStartState();
692       break;
693     case ATNState::STAR_BLOCK_START :
694       s = new StarBlockStartState();
695       break;
696     case ATNState::TOKEN_START :
697       s = new TokensStartState();
698       break;
699     case ATNState::RULE_STOP :
700       s = new RuleStopState();
701       break;
702     case ATNState::BLOCK_END :
703       s = new BlockEndState();
704       break;
705     case ATNState::STAR_LOOP_BACK :
706       s = new StarLoopbackState();
707       break;
708     case ATNState::STAR_LOOP_ENTRY :
709       s = new StarLoopEntryState();
710       break;
711     case ATNState::PLUS_LOOP_BACK :
712       s = new PlusLoopbackState();
713       break;
714     case ATNState::LOOP_END :
715       s = new LoopEndState();
716       break;
717     default :
718       std::string message = "The specified state type " + std::to_string(type) + " is not valid.";
719       throw IllegalArgumentException(message);
720   }
721 
722   s->ruleIndex = ruleIndex;
723   return s;
724 }
725 
lexerActionFactory(LexerActionType type,int data1,int data2)726 Ref<LexerAction> ATNDeserializer::lexerActionFactory(LexerActionType type, int data1, int data2) {
727   switch (type) {
728     case LexerActionType::CHANNEL:
729       return std::make_shared<LexerChannelAction>(data1);
730 
731     case LexerActionType::CUSTOM:
732       return std::make_shared<LexerCustomAction>(data1, data2);
733 
734     case LexerActionType::MODE:
735       return std::make_shared< LexerModeAction>(data1);
736 
737     case LexerActionType::MORE:
738       return LexerMoreAction::getInstance();
739 
740     case LexerActionType::POP_MODE:
741       return LexerPopModeAction::getInstance();
742 
743     case LexerActionType::PUSH_MODE:
744       return std::make_shared<LexerPushModeAction>(data1);
745 
746     case LexerActionType::SKIP:
747       return LexerSkipAction::getInstance();
748 
749     case LexerActionType::TYPE:
750       return std::make_shared<LexerTypeAction>(data1);
751 
752     default:
753       throw IllegalArgumentException("The specified lexer action type " + std::to_string(static_cast<size_t>(type)) +
754                                      " is not valid.");
755   }
756 }
757