antlr4 0.9.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (64) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +27 -0
  3. data/README.md +46 -0
  4. data/lib/antlr4.rb +262 -0
  5. data/lib/antlr4/BufferedTokenStream.rb +306 -0
  6. data/lib/antlr4/CommonTokenFactory.rb +53 -0
  7. data/lib/antlr4/CommonTokenStream.rb +56 -0
  8. data/lib/antlr4/FileStream.rb +14 -0
  9. data/lib/antlr4/InputStream.rb +82 -0
  10. data/lib/antlr4/IntervalSet.rb +341 -0
  11. data/lib/antlr4/LL1Analyzer.rb +177 -0
  12. data/lib/antlr4/Lexer.rb +335 -0
  13. data/lib/antlr4/ListTokenSource.rb +140 -0
  14. data/lib/antlr4/Parser.rb +562 -0
  15. data/lib/antlr4/ParserInterpreter.rb +149 -0
  16. data/lib/antlr4/ParserRuleContext.rb +162 -0
  17. data/lib/antlr4/PredictionContext.rb +690 -0
  18. data/lib/antlr4/Recognizer.rb +162 -0
  19. data/lib/antlr4/RuleContext.rb +226 -0
  20. data/lib/antlr4/Token.rb +124 -0
  21. data/lib/antlr4/TokenFactory.rb +3 -0
  22. data/lib/antlr4/TokenSource.rb +4 -0
  23. data/lib/antlr4/TokenStream.rb +3 -0
  24. data/lib/antlr4/TraceListener.rb +23 -0
  25. data/lib/antlr4/atn/ATN.rb +133 -0
  26. data/lib/antlr4/atn/ATNConfig.rb +146 -0
  27. data/lib/antlr4/atn/ATNConfigSet.rb +215 -0
  28. data/lib/antlr4/atn/ATNDeserializationOptions.rb +62 -0
  29. data/lib/antlr4/atn/ATNDeserializer.rb +604 -0
  30. data/lib/antlr4/atn/ATNSimulator.rb +43 -0
  31. data/lib/antlr4/atn/ATNState.rb +253 -0
  32. data/lib/antlr4/atn/ATNType.rb +22 -0
  33. data/lib/antlr4/atn/LexerATNSimulator.rb +612 -0
  34. data/lib/antlr4/atn/LexerAction.rb +311 -0
  35. data/lib/antlr4/atn/LexerActionExecutor.rb +134 -0
  36. data/lib/antlr4/atn/ParserATNSimulator.rb +1622 -0
  37. data/lib/antlr4/atn/PredictionMode.rb +525 -0
  38. data/lib/antlr4/atn/SemanticContext.rb +355 -0
  39. data/lib/antlr4/atn/Transition.rb +297 -0
  40. data/lib/antlr4/base.rb +60 -0
  41. data/lib/antlr4/dfa/DFA.rb +128 -0
  42. data/lib/antlr4/dfa/DFASerializer.rb +77 -0
  43. data/lib/antlr4/dfa/DFAState.rb +133 -0
  44. data/lib/antlr4/error.rb +151 -0
  45. data/lib/antlr4/error/DiagnosticErrorListener.rb +136 -0
  46. data/lib/antlr4/error/ErrorListener.rb +109 -0
  47. data/lib/antlr4/error/ErrorStrategy.rb +742 -0
  48. data/lib/antlr4/tree/Chunk.rb +31 -0
  49. data/lib/antlr4/tree/ParseTreeMatch.rb +105 -0
  50. data/lib/antlr4/tree/ParseTreePattern.rb +70 -0
  51. data/lib/antlr4/tree/ParseTreePatternMatcher.rb +334 -0
  52. data/lib/antlr4/tree/RuleTagToken.rb +39 -0
  53. data/lib/antlr4/tree/TokenTagToken.rb +38 -0
  54. data/lib/antlr4/tree/Tree.rb +204 -0
  55. data/lib/antlr4/tree/Trees.rb +111 -0
  56. data/lib/antlr4/version.rb +5 -0
  57. data/lib/antlr4/xpath/XPath.rb +354 -0
  58. data/lib/double_key_map.rb +78 -0
  59. data/lib/java_symbols.rb +24 -0
  60. data/lib/uuid.rb +87 -0
  61. data/test/test_intervalset.rb +664 -0
  62. data/test/test_tree.rb +140 -0
  63. data/test/test_uuid.rb +122 -0
  64. metadata +109 -0
@@ -0,0 +1,60 @@
1
+
2
+ module Antlr4
3
+ INVALID_INTERVAL = Range.new(-1, -2)
4
+ end
5
+
6
+ class Range
7
+ def stop
8
+ last
9
+ end
10
+ def start
11
+ first
12
+ end
13
+ def length
14
+ size
15
+ end
16
+ def a
17
+ first
18
+ end
19
+ def b
20
+ last
21
+ end
22
+ end
23
+
24
+
25
+ class String
26
+ def is_uppercase?
27
+ self == self.upcase
28
+ end
29
+ def escapeWhitespace(escapeSpaces=false)
30
+ if escapeSpaces then
31
+ c = "\xB7"
32
+ else
33
+ c = " "
34
+ end
35
+ gsub(" ", c).gsub("\t","\\t").gsub("\n","\\n").gsub("\r","\\r")
36
+ end
37
+ end
38
+
39
+ class Hash
40
+ def get(x,y)
41
+ return fetch(x) if self.has_key? x
42
+ return y
43
+ end
44
+ end
45
+
46
+
47
+ class Set
48
+ def remove(a)
49
+ delete(a)
50
+ end
51
+ end
52
+
53
+ class Object
54
+
55
+ def type_check(o, t)
56
+ unless o.kind_of? t
57
+ raise Exception.new("Fail Type Check! #{o.class} is not kind of #{t}" )
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,128 @@
1
+
2
+ class DFA
3
+ attr_accessor :atnStartState, :decision, :_states, :s0, :precedenceDfa
4
+ def initialize(_atnStartState, _decision=0)
5
+ raise Exception.new("atnStartState is nil") if _atnStartState.nil?
6
+ type_check(_decision, Fixnum)
7
+ type_check(_atnStartState, ATNState)
8
+ # From which ATN state did we create this DFA?
9
+ @atnStartState = _atnStartState
10
+ @decision = _decision
11
+ # A set of all DFA states. Use {@link Map} so we can get old state back
12
+ # ({@link Set} only allows you to see if it's there).
13
+ @_states = Hash.new
14
+ @s0 = nil
15
+ # {@code true} if this DFA is for a precedence decision; otherwise,
16
+ # {@code false}. This is the backing field for {@link #isPrecedenceDfa},
17
+ # {@link #setPrecedenceDfa}.
18
+ @precedenceDfa = false
19
+ end
20
+ def isPrecedenceDfa
21
+ @precedenceDfa
22
+ end
23
+ # Get the start state for a specific precedence value.
24
+ #
25
+ # @param precedence The current precedence.
26
+ # @return The start state corresponding to the specified precedence, or
27
+ # {@code null} if no start state exists for the specified precedence.
28
+ #
29
+ # @throws IllegalStateException if this is not a precedence DFA.
30
+ # @see #isPrecedenceDfa()
31
+
32
+ def getPrecedenceStartState(precedence)
33
+ if not self.precedenceDfa then
34
+ raise IllegalStateException.new("Only precedence DFAs may contain a precedence start state.")
35
+ end
36
+ # s0.edges is never null for a precedence DFA
37
+ if precedence < 0 or precedence >= self.s0.edges.length then
38
+ return nil
39
+ end
40
+ return self.s0.edges[precedence]
41
+ end
42
+
43
+ # Set the start state for a specific precedence value.
44
+ #
45
+ # @param precedence The current precedence.
46
+ # @param startState The start state corresponding to the specified
47
+ # precedence.
48
+ #
49
+ # @throws IllegalStateException if this is not a precedence DFA.
50
+ # @see #isPrecedenceDfa()
51
+ #
52
+ def setPrecedenceStartState(precedence, startState)
53
+ if not self.precedenceDfa then
54
+ raise IllegalStateException.new("Only precedence DFAs may contain a precedence start state.")
55
+ end
56
+ if precedence < 0
57
+ return
58
+ end
59
+ # synchronization on s0 here is ok. when the DFA is turned into a
60
+ # precedence DFA, s0 will be initialized once and not updated again
61
+ # s0.edges is never null for a precedence DFA
62
+ self.s0.edges[precedence] = startState
63
+ end
64
+ #
65
+ # Sets whether this is a precedence DFA. If the specified value differs
66
+ # from the current DFA configuration, the following actions are taken;
67
+ # otherwise no changes are made to the current DFA.
68
+ #
69
+ # <ul>
70
+ # <li>The {@link #states} map is cleared</li>
71
+ # <li>If {@code precedenceDfa} is {@code false}, the initial state
72
+ # {@link #s0} is set to {@code null}; otherwise, it is initialized to a new
73
+ # {@link DFAState} with an empty outgoing {@link DFAState#edges} array to
74
+ # store the start states for individual precedence values.</li>
75
+ # <li>The {@link #precedenceDfa} field is updated</li>
76
+ # </ul>
77
+ #
78
+ # @param precedenceDfa {@code true} if this is a precedence DFA; otherwise,
79
+ # {@code false}
80
+
81
+ def setPrecedenceDfa(_precedenceDfa)
82
+ if self.precedenceDfa != _precedenceDfa then
83
+ self._states = Hash.new
84
+ if _precedenceDfa then
85
+ precedenceState = DFAState.new(nil, ATNConfigSet.new())
86
+ precedenceState.edges = Array.new
87
+ precedenceState.isAcceptState = false
88
+ precedenceState.requiresFullContext = false
89
+ self.s0 = precedenceState
90
+ else
91
+ self.s0 = nil
92
+ end
93
+ self.precedenceDfa = _precedenceDfa
94
+ end
95
+ end
96
+
97
+ def states()
98
+ self._states
99
+ end
100
+
101
+ # Return a list of all states in this DFA, ordered by state number.
102
+ def sortedStates()
103
+ return self._states.keys().sort {|a,b| a.stateNumber <=> b.stateNumber}
104
+ end
105
+
106
+ def to_s
107
+ toString()
108
+ end
109
+ def inspect
110
+ "<DFA #{atnStartState.inspect} decision(#{@decision}) states(#{states.length}) >"
111
+ end
112
+
113
+ def toString(tokenNames=nil)
114
+ if self.s0.nil? then
115
+ return ''
116
+ end
117
+ serializer = DFASerializer.new(self,tokenNames)
118
+ return serializer.to_s
119
+ end
120
+
121
+ def toLexerString
122
+ if self.s0.nil? then
123
+ return ''
124
+ end
125
+ serializer = LexerDFASerializer.new(self)
126
+ return serializer.to_s
127
+ end
128
+ end
@@ -0,0 +1,77 @@
1
+ # A DFA walker that knows how to dump them to serialized strings.
2
+
3
+ class DFASerializer
4
+
5
+ attr_accessor :dfa, :tokenNames
6
+ def initialize(dfa, tokenNames=nil)
7
+ @dfa = dfa
8
+ @tokenNames = tokenNames
9
+ end
10
+
11
+ def to_s
12
+ return nil if self.dfa.s0.nil?
13
+ StringIO.open do |buf|
14
+ self.dfa.sortedStates().each do |s|
15
+ n = 0
16
+ if not s.edges.nil?
17
+ n = s.edges.length
18
+ end
19
+ for i in 0..(n-1) do
20
+ t = s.edges[i]
21
+ if not t.nil? and t.stateNumber != 0x7FFFFFFF then
22
+ buf.write(self.getStateString(s))
23
+ label = self.getEdgeLabel(i)
24
+ buf.write("-")
25
+ buf.write(label)
26
+ buf.write("->")
27
+ buf.write(self.getStateString(t))
28
+ buf.write("\n")
29
+ end
30
+ end
31
+ end
32
+ output = buf.string()
33
+ if output.length == 0
34
+ return nil
35
+ else
36
+ return output
37
+ end
38
+ end
39
+ end
40
+
41
+ def getEdgeLabel(i)
42
+ return "EOF" if i==0
43
+ if not self.tokenNames.nil? then
44
+ return self.tokenNames[i-1]
45
+ else
46
+ return (i-1).to_s
47
+ end
48
+ end
49
+
50
+ def getStateString(s)
51
+ # s_acceptState = nil
52
+ # s_acceptState = ":" if s.isAcceptState
53
+ s_requireContext = nil
54
+ s_requireContext = "^" if s.requiresFullContext
55
+ baseStateStr = "s#{s.stateNumber}#{s_requireContext}"
56
+ if s.isAcceptState then
57
+ if not s.predicates.nil? then
58
+ return ":#{baseStateStr}=>#{s.predicates}"
59
+ else
60
+ return ":#{baseStateStr}=>#{s.prediction}"
61
+ end
62
+ else
63
+ return baseStateStr
64
+ end
65
+ end
66
+ end
67
+
68
+ class LexerDFASerializer < DFASerializer
69
+
70
+ def initialize(dfa)
71
+ super(dfa, nil)
72
+ end
73
+
74
+ def getEdgeLabel(i)
75
+ return "'#{[i].pack('U')}'"
76
+ end
77
+ end
@@ -0,0 +1,133 @@
1
+ # Map a predicate to a predicted alternative.
2
+
3
+ class PredPrediction
4
+ attr_accessor :pred, :alt
5
+ def initialize(pred, alt)
6
+ @alt = alt
7
+ @pred = pred
8
+ end
9
+
10
+ def to_s
11
+ "(#{self.pred}, #{self.alt})"
12
+ end
13
+ end
14
+ # A DFA state represents a set of possible ATN configurations.
15
+ # As Aho, Sethi, Ullman p. 117 says "The DFA uses its state
16
+ # to keep track of all possible states the ATN can be in after
17
+ # reading each input symbol. That is to say, after reading
18
+ # input a1a2..an, the DFA is in a state that represents the
19
+ # subset T of the states of the ATN that are reachable from the
20
+ # ATN's start state along some path labeled a1a2..an."
21
+ # In conventional NFA&rarr;DFA conversion, therefore, the subset T
22
+ # would be a bitset representing the set of states the
23
+ # ATN could be in. We need to track the alt predicted by each
24
+ # state as well, however. More importantly, we need to maintain
25
+ # a stack of states, tracking the closure operations as they
26
+ # jump from rule to rule, emulating rule invocations (method calls).
27
+ # I have to add a stack to simulate the proper lookahead sequences for
28
+ # the underlying LL grammar from which the ATN was derived.
29
+ #
30
+ # <p>I use a set of ATNConfig objects not simple states. An ATNConfig
31
+ # is both a state (ala normal conversion) and a RuleContext describing
32
+ # the chain of rules (if any) followed to arrive at that state.</p>
33
+ #
34
+ # <p>A DFA state may have multiple references to a particular state,
35
+ # but with different ATN contexts (with same or different alts)
36
+ # meaning that state was reached via a different set of rule invocations.</p>
37
+ #/
38
+ class DFAState
39
+ attr_accessor :stateNumber, :configs, :edges, :isAcceptState, :prediction
40
+ attr_accessor :lexerActionExecutor, :requiresFullContext, :predicates
41
+ def initialize(state_number=nil, _configs=ATNConfigSet.new())
42
+ if state_number.nil? then
43
+ @stateNumber = -1
44
+ else
45
+ @stateNumber = state_number
46
+ end
47
+ self.configs = _configs
48
+ # {@code edges[symbol]} points to target of symbol. Shift up by 1 so (-1)
49
+ # {@link Token#EOF} maps to {@code edges[0]}.
50
+ self.edges = nil
51
+ self.isAcceptState = false
52
+ # if accept state, what ttype do we match or alt do we predict?
53
+ # This is set to {@link ATN#INVALID_ALT_NUMBER} when {@link #predicates}{@code !=null} or
54
+ # {@link #requiresFullContext}.
55
+ self.prediction = 0
56
+ self.lexerActionExecutor = nil
57
+ # Indicates that this state was created during SLL prediction that
58
+ # discovered a conflict between the configurations in the state. Future
59
+ # {@link ParserATNSimulator#execATN} invocations immediately jumped doing
60
+ # full context prediction if this field is true.
61
+ self.requiresFullContext = false
62
+ # During SLL parsing, this is a list of predicates associated with the
63
+ # ATN configurations of the DFA state. When we have predicates,
64
+ # {@link #requiresFullContext} is {@code false} since full context prediction evaluates predicates
65
+ # on-the-fly. If this is not null, then {@link #prediction} is
66
+ # {@link ATN#INVALID_ALT_NUMBER}.
67
+ #
68
+ # <p>We only use these for non-{@link #requiresFullContext} but conflicting states. That
69
+ # means we know from the context (it's $ or we don't dip into outer
70
+ # context) that it's an ambiguity not a conflict.</p>
71
+ #
72
+ # <p>This list is computed by {@link ParserATNSimulator#predicateDFAState}.</p>
73
+ self.predicates = nil
74
+ end
75
+
76
+ # Get the set of all alts mentioned by all ATN configurations in this
77
+ # DFA state.
78
+ def getAltSet()
79
+ alts = Set.new
80
+ if not self.configs.nil?
81
+ for c in self.configs do
82
+ alts.add(c.alt)
83
+ end
84
+ end
85
+ if alts.empty?
86
+ return nil
87
+ else
88
+ return alts
89
+ end
90
+ end
91
+ def <=>(other)
92
+ self.configs <=> other.configs
93
+ end
94
+ def hash()
95
+ self.configs.hash
96
+ end
97
+ # Two {@link DFAState} instances are equal if their ATN configuration sets
98
+ # are the same. This method is used to see if a state already exists.
99
+ #
100
+ # <p>Because the number of alternatives and number of ATN configurations are
101
+ # finite, there is a finite number of DFA states that can be processed.
102
+ # This is necessary to show that the algorithm terminates.</p>
103
+ #
104
+ # <p>Cannot test the DFA state numbers here because in
105
+ # {@link ParserATNSimulator#addDFAState} we need to know if any other state
106
+ # exists that has this exact set of ATN configurations. The
107
+ # {@link #stateNumber} is irrelevant.</p>
108
+ def eql?(other)
109
+ self == other
110
+ end
111
+ def ==(other)
112
+ # compare set of ATN configurations in this set with other
113
+ return true if self.equal?(other)
114
+ other.kind_of?(DFAState) and self.configs==other.configs
115
+ end
116
+
117
+ def to_s
118
+ StringIO.open do |buf|
119
+ buf.write(self.stateNumber.to_s)
120
+ buf.write(":")
121
+ buf.write(self.configs.to_s )
122
+ if self.isAcceptState then
123
+ buf.write("=>")
124
+ if self.predicates then
125
+ buf.write(self.predicates.to_s)
126
+ else
127
+ buf.write(self.prediction.to_s)
128
+ end
129
+ end
130
+ return buf.string
131
+ end
132
+ end
133
+ end
@@ -0,0 +1,151 @@
1
+
2
+ class UnsupportedOperationException < Exception
3
+ end
4
+
5
+ class IllegalStateException < Exception
6
+ end
7
+
8
+ class CancellationException < IllegalStateException
9
+ end
10
+
11
+ # The root of the ANTLR exception hierarchy. In general, ANTLR tracks just
12
+ # 3 kinds of errors: prediction errors, failed predicate errors, and
13
+ # mismatched input errors. In each case, the parser knows where it is
14
+ # in the input, where it is in the ATN, the rule invocation stack,
15
+ # and what kind of problem occurred.
16
+
17
+ class RecognitionException < Exception
18
+
19
+ attr_accessor :recognizer, :input, :ctx, :offendingState, :offendingToken
20
+ # used by subclassees
21
+ attr_accessor :deadEndConfigs, :startToken
22
+ def initialize(message=nil, recognizer=nil, input=nil, ctx=nil)
23
+ super(message)
24
+ @recognizer = recognizer
25
+ @input = input
26
+ @ctx = ctx
27
+ # The current {@link Token} when an error occurred. Since not all streams
28
+ # support accessing symbols by index, we have to track the {@link Token}
29
+ # instance itself.
30
+ @offendingToken = nil
31
+ # Get the ATN state number the parser was in at the time the error
32
+ # occurred. For {@link NoViableAltException} and
33
+ # {@link LexerNoViableAltException} exceptions, this is the
34
+ # {@link DecisionState} number. For others, it is the state whose outgoing
35
+ # edge we couldn't match.
36
+ @offendingState = -1
37
+ if recognizer then
38
+ @offendingState = recognizer.state
39
+ end
40
+ end
41
+
42
+ # <p>If the state number is not known, this method returns -1.</p>
43
+
44
+ #
45
+ # Gets the set of input symbols which could potentially follow the
46
+ # previously matched symbol at the time this exception was thrown.
47
+ #
48
+ # <p>If the set of expected tokens is not known and could not be computed,
49
+ # this method returns {@code null}.</p>
50
+ #
51
+ # @return The set of token types that could potentially follow the current
52
+ # state in the ATN, or {@code null} if the information is not available.
53
+ #/
54
+ def getExpectedTokens()
55
+ if self.recognizer then
56
+ @offendingState = recognizer.state
57
+ return self.recognizer.atn.getExpectedTokens(self.offendingState, self.ctx)
58
+ else
59
+ return nil
60
+ end
61
+ end
62
+ end
63
+
64
+
65
+ class LexerNoViableAltException < RecognitionException
66
+
67
+ attr_accessor :startIndex
68
+ def initialize(lexer, input, startIndex, deadEndConfigs)
69
+ super(nil, lexer, input, nil)
70
+ @startIndex = startIndex
71
+ @deadEndConfigs = deadEndConfigs
72
+ end
73
+
74
+ def to_s
75
+ symbol = nil
76
+ if self.startIndex >= 0 and self.startIndex < self.input.size() then
77
+ symbol = self.input.getText(self.startIndex, self.startIndex)
78
+ # TODO symbol = Utils.escapeWhitespace(symbol, false);
79
+ end
80
+ return "LexerNoViableAltException #{symbol}"
81
+ end
82
+ end
83
+ # Indicates that the parser could not decide which of two or more paths
84
+ # to take based upon the remaining input. It tracks the starting token
85
+ # of the offending input and also knows where the parser was
86
+ # in the various paths when the error. Reported by reportNoViableAlternative()
87
+ #
88
+ class NoViableAltException < RecognitionException
89
+
90
+ def initialize(recognizer, input=nil, startToken=nil, offendingToken=nil, deadEndConfigs=nil, ctx=nil)
91
+ ctx = recognizer.ctx if ctx.nil?
92
+ offendingToken = recognizer.getCurrentToken() if offendingToken.nil?
93
+ startToken = recognizer.getCurrentToken() if startToken.nil?
94
+ input = recognizer.getInputStream() if input.nil?
95
+ super(nil,recognizer, input, ctx)
96
+ # Which configurations did we try at input.index() that couldn't match input.LT(1)?#
97
+ @deadEndConfigs = deadEndConfigs
98
+ # The token object at the start index; the input stream might
99
+ # not be buffering tokens so get a reference to it. (At the
100
+ # time the error occurred, of course the stream needs to keep a
101
+ # buffer all of the tokens but later we might not have access to those.)
102
+ @startToken = startToken
103
+ @offendingToken = offendingToken
104
+ end
105
+ end
106
+ # This signifies any kind of mismatched input exceptions such as
107
+ # when the current input does not match the expected token.
108
+ #
109
+ class InputMismatchException < RecognitionException
110
+
111
+ def initiailze(recognizer)
112
+ super(nil, recognizer, recognizer.getInputStream(), recognizer.ctx)
113
+ @offendingToken = recognizer.getCurrentToken()
114
+ end
115
+ end
116
+
117
+ # A semantic predicate failed during validation. Validation of predicates
118
+ # occurs when normally parsing the alternative just like matching a token.
119
+ # Disambiguating predicate evaluation occurs when we test a predicate during
120
+ # prediction.
121
+
122
+ class FailedPredicateException < RecognitionException
123
+
124
+ attr_accessor :ruleIndex,:predicateIndex, :predicate
125
+ def initialize(recognizer, predicate=nil, message=nil)
126
+ super(self.formatMessage(predicate,message), recognizer,
127
+ recognizer.getInputStream(), recognizer.ctx)
128
+ s = recognizer.interp.atn.states[recognizer.state]
129
+ trans = s.transitions[0]
130
+ if trans.kind_of? PredicateTransition then
131
+ @ruleIndex = trans.ruleIndex
132
+ @predicateIndex = trans.predIndex
133
+ else
134
+ @ruleIndex = 0
135
+ @predicateIndex = 0
136
+ end
137
+ @predicate = predicate
138
+ @offendingToken = recognizer.getCurrentToken()
139
+ end
140
+
141
+ def formatMessage(predicate, message)
142
+ if message.nil?
143
+ "failed predicate: {" + predicate + "}?"
144
+ else
145
+ message
146
+ end
147
+ end
148
+ end
149
+
150
+ class ParseCancellationException < CancellationException
151
+ end