1324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver#!/usr/bin/ruby 2324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# encoding: utf-8 3324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 4324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverrequire 'antlr3' 5324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 6324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin LICENSE 7324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 8324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver[The "BSD licence"] 9324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverCopyright (c) 2009-2010 Kyle Yetter 10324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverAll rights reserved. 11324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 12324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverRedistribution and use in source and binary forms, with or without 13324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodification, are permitted provided that the following conditions 14324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverare met: 15324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 16324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 1. Redistributions of source code must retain the above copyright 17324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver notice, this list of conditions and the following disclaimer. 18324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 2. Redistributions in binary form must reproduce the above copyright 19324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver notice, this list of conditions and the following disclaimer in the 20324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver documentation and/or other materials provided with the distribution. 21324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 3. The name of the author may not be used to endorse or promote products 22324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver derived from this software without specific prior written permission. 23324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 24324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverTHIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 25324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverIMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 26324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverOF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 27324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverIN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 28324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverINCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 29324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverNOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 30324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverDATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 31324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverTHEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 32324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 33324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverTHIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 35324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 36324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 37324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodule ANTLR3 38324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 39324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin rdoc ANTLR3::Debug 40324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 41324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverNamespace for all debugging-related class and module definitions. 42324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 43324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 44324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 45324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodule Debug 46324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 47324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverDEFAULT_PORT = 49100 48324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 49324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# since there are many components to the debug-mode 50324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# section of the antlr3 runtime library, most of which 51324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# are not used simultaneously, debug.rb contains the 52324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# base of the debug library and the various listeners 53324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver# and tree-related code are autloaded on-demand 54324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :EventSocketProxy, 'antlr3/debug/socket' 55324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :RemoteEventSocketListener, 'antlr3/debug/socket' 56324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :TraceEventListener, 'antlr3/debug/trace-event-listener' 57324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :RecordEventListener, 'antlr3/debug/record-event-listener' 58324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :RuleTracer, 'antlr3/debug/rule-tracer' 59324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :EventHub, 'antlr3/debug/event-hub' 60324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :TreeAdaptor, 'antlr3/tree/debug' 61324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverautoload :TreeNodeStream, 'antlr3/tree/debug' 62324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 63324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverRecognizerSharedState = Struct.new( 64324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the rule invocation depth 65324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :rule_invocation_stack, 66324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # a boolean flag to indicate whether or not the current decision is cyclic 67324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :cyclic_decision, 68324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # a stack that tracks follow sets for error recovery 69324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :following, 70324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # a flag indicating whether or not the recognizer is in error recovery mode 71324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :error_recovery, 72324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the index in the input stream of the last error 73324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :last_error_index, 74324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # tracks the backtracking depth 75324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :backtracking, 76324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # if a grammar is compiled with the memoization option, this will 77324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # be set to a hash mapping previously parsed rules to cached indices 78324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :rule_memory, 79324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # tracks the number of syntax errors seen so far 80324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :syntax_errors, 81324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # holds newly constructed tokens for lexer rules 82324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :token, 83324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the input stream index at which the token starts 84324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :token_start_position, 85324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the input stream line number at which the token starts 86324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :token_start_line, 87324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the input stream column at which the token starts 88324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :token_start_column, 89324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the channel value of the target token 90324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :channel, 91324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the type value of the target token 92324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :type, 93324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the text of the target token 94324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :text 95324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver) 96324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 97324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin rdoc ANTLR3::Debug::RecognizerSharedState 98324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 99324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverANTLR3::Debug::RecognizerSharedState is identical to 100324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverANTLR3::RecognizerSharedState, but adds additional fields used for recognizers 101324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvergenerated in debug or profiling mode. 102324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 103324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 104324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverclass RecognizerSharedState 105324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def initialize 106324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super( [], false, [], false, -1, 0, nil, 0, nil, -1 ) 107324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # ^-- same as this --v 108324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.following = [] 109324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.error_recovery = false 110324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.last_error_index = -1 111324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.backtracking = 0 112324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.syntax_errors = 0 113324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.rule_level = 0 114324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # self.token_start_position = -1 115324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 116324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 117324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def reset! 118324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.following.clear 119324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.error_recovery = false 120324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.last_error_index = -1 121324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.backtracking = 0 122324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.rule_memory and rule_memory.clear 123324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.syntax_errors = 0 124324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.token = nil 125324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.token_start_position = -1 126324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.token_start_line = nil 127324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.token_start_column = nil 128324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.channel = nil 129324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.type = nil 130324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.text = nil 131324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver self.rule_invocation_stack.clear 132324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 133324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 134324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 135324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 136324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin rdoc ANTLR3::Debug::ParserEvents 137324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 138324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverParserEvents adds debugging event hook methods and functionality that is 139324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverrequired by the code ANTLR generated when called with the <tt>-debug</tt> 140324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverswitch. 141324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 142324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 143324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodule ParserEvents 144324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver include ANTLR3::Error 145324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 146324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def self.included( klass ) 147324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super 148324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver if klass.is_a?( ::Class ) 149324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def klass.debug? 150324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver true 151324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 152324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 153324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 154324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 155324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 156324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver attr_reader :debug_listener 157324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 158324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def initialize( stream, options = {} ) 159324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener = options[ :debug_listener ] ||= begin 160324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver EventSocketProxy.new( self, options ).handshake 161324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 162324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver options[ :state ] ||= Debug::RecognizerSharedState.new 163324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super( stream, options ) 164324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver if @input.is_a?( Debug::TokenStream ) 165324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @input.debug_listener ||= @debug_listener 166324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver else 167324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @input = Debug::TokenStream.wrap( @input, @debug_listener ) 168324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 169324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 170324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 171324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def rule_level 172324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.length 173324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 174324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 175324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def cyclic_decision? 176324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.cyclic_decision 177324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 178324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 179324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def cyclic_decision=( flag ) 180324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.cyclic_decision = flag 181324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 182324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 183324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # custom attribute writer for debug_listener 184324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # propegates the change in listener to the 185324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # parser's debugging input stream 186324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def debug_listener=( dbg ) 187324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener = dbg 188324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @input.debug_listener = dbg rescue nil 189324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 190324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 191324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def begin_resync 192324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.begin_resync 193324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super 194324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 195324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 196324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def end_resync 197324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.end_resync 198324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super 199324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 200324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 201324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # TO-DO: is this pointless? 202324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def resync 203324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver begin_resync 204324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver yield( self ) 205324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ensure 206324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end_resync 207324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 208324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 209324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def begin_backtrack 210324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.begin_backtrack( @state.backtracking ) 211324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 212324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 213324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def end_backtrack( successful ) 214324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.end_backtrack( @state.backtracking, successful ) 215324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 216324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 217324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def backtrack 218324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.backtracking += 1 219324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.begin_backtrack( @state.backtracking ) 220324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver start = @input.mark 221324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver success = 222324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver begin yield 223324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver rescue BacktrackingFailed then false 224324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver else true 225324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 226324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return success 227324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ensure 228324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @input.rewind( start ) 229324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.end_backtrack( @state.backtracking, ( success rescue nil ) ) 230324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.backtracking -= 1 231324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 232324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 233324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def report_error( exc ) 234324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ANTLR3::RecognitionError === exc and 235324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.recognition_exception( exc ) 236324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super 237324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 238324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 239324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def missing_symbol( error, expected_type, follow ) 240324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver symbol = super 241324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.consume_node( symbol ) 242324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return( symbol ) 243324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 244324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 245324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def in_rule( grammar_file, rule_name ) 246324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.empty? and @debug_listener.commence 247324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.enter_rule( grammar_file, rule_name ) 248324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.push( grammar_file, rule_name ) 249324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver yield 250324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ensure 251324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.pop( 2 ) 252324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.exit_rule( grammar_file, rule_name ) 253324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.empty? and @debug_listener.terminate 254324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 255324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 256324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def rule_invocation_stack 257324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @state.rule_invocation_stack.each_slice( 2 ).to_a 258324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 259324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 260324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def predicate?( description ) 261324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver result = yield 262324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.semantic_predicate( result, description ) 263324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return result 264324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 265324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 266324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def in_alternative( alt_number ) 267324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.enter_alternative( alt_number ) 268324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 269324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 270324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def in_subrule( decision_number ) 271324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.enter_subrule( decision_number ) 272324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver yield 273324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ensure 274324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.exit_subrule( decision_number ) 275324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 276324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 277324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def in_decision( decision_number ) 278324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.enter_decision( decision_number ) 279324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver yield 280324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ensure 281324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.exit_decision( decision_number ) 282324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 283324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 284324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 285324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 286324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin rdoc ANTLR3::Debug::TokenStream 287324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 288324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverA module that wraps token stream methods with debugging event code. A debuggable 289324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverparser will <tt>extend</tt> its input stream with this module if the stream is 290324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvernot already a Debug::TokenStream. 291324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 292324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 293324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodule TokenStream 294324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 295324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def self.wrap( stream, debug_listener = nil ) 296324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver stream.extend( self ) 297324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver stream.instance_eval do 298324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @initial_stream_state = true 299324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener = debug_listener 300324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @last_marker = nil 301324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 302324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return( stream ) 303324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 304324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver attr_reader :last_marker 305324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver attr_accessor :debug_listener 306324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 307324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def consume 308324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @initial_stream_state and consume_initial_hidden_tokens 309324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver a = index + 1 # the next position IF there are no hidden tokens in between 310324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver t = super 311324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver b = index # the actual position after consuming 312324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.consume_token( t ) if @debug_listener 313324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 314324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # if b > a, report the consumption of hidden tokens 315324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver for i in a...b 316324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.consume_hidden_token at( i ) 317324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 318324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 319324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 320324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 321324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # after a token stream fills up its buffer 322324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # by exhausting its token source, it may 323324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # skip to an initial position beyond the first 324324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # actual token, if there are hidden tokens 325324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # at the beginning of the stream. 326324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # 327324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # This private method is used to 328324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # figure out if any hidden tokens 329324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # were skipped initially, and then 330324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # report their consumption to 331324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the debug listener 332324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def consume_initial_hidden_tokens 333324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver first_on_channel_token_index = self.index 334324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver first_on_channel_token_index.times do |index| 335324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.consume_hidden_token at( index ) 336324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 337324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @initial_stream_state = false 338324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 339324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 340324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver private :consume_initial_hidden_tokens 341324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 342324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ############################################################################################ 343324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ###################################### Stream Methods ###################################### 344324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ############################################################################################ 345324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 346324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def look( steps = 1 ) 347324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @initial_stream_state and consume_initial_hidden_tokens 348324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver token = super( steps ) 349324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.look( steps, token ) 350324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return token 351324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 352324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 353324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def peek( steps = 1 ) 354324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver look( steps ).type 355324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 356324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 357324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def mark 358324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @last_marker = super 359324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.mark( @last_marker ) 360324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver return @last_marker 361324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 362324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 363324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def rewind( marker = nil, release = true ) 364324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver @debug_listener.rewind( marker ) 365324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver super 366324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 367324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 368324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 369324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=begin rdoc ANTLR3::Debug::EventListener 370324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 371324c4644fee44b9898524c09511bd33c3f12e2dfBen GruverA listener that simply records text representations of the events. Useful for debugging the 372324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverdebugging facility ;) Subclasses can override the record() method (which defaults to printing 373324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverto stdout) to record the events in a different way. 374324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 375324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver=end 376324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruvermodule EventListener 377324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver PROTOCOL_VERSION = '2' 378324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The parser has just entered a rule. No decision has been made about 379324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # which alt is predicted. This is fired AFTER init actions have been 380324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # executed. Attributes are defined and available etc... 381324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The grammarFileName allows composite grammars to jump around among 382324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # multiple grammar files. 383324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 384324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def enter_rule( grammar_file, rule_name ) 385324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 386324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 387324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 388324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Because rules can have lots of alternatives, it is very useful to 389324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # know which alt you are entering. This is 1..n for n alts. 390324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 391324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def enter_alternative( alt ) 392324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 393324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 394324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 395324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # This is the last thing executed before leaving a rule. It is 396324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # executed even if an exception is thrown. This is triggered after 397324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # error reporting and recovery have occurred (unless the exception is 398324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # not caught in this rule). This implies an "exitAlt" event. 399324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The grammarFileName allows composite grammars to jump around among 400324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # multiple grammar files. 401324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 402324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def exit_rule( grammar_file, rule_name ) 403324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 404324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 405324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 406324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Track entry into any (...) subrule other EBNF construct 407324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 408324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def enter_subrule( decision_number ) 409324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 410324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 411324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 412324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def exit_subrule( decision_number ) 413324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 414324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 415324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 416324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Every decision, fixed k or arbitrary, has an enter/exit event 417324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # so that a GUI can easily track what look/consume events are 418324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # associated with prediction. You will see a single enter/exit 419324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # subrule but multiple enter/exit decision events, one for each 420324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # loop iteration. 421324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 422324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def enter_decision( decision_number ) 423324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 424324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 425324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 426324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def exit_decision( decision_number ) 427324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 428324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 429324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 430324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # An input token was consumed; matched by any kind of element. 431324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Trigger after the token was matched by things like match(), matchAny(). 432324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 433324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def consume_token( tree ) 434324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 435324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 436324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 437324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # An off-channel input token was consumed. 438324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Trigger after the token was matched by things like match(), matchAny(). 439324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # (unless of course the hidden token is first stuff in the input stream). 440324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 441324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def consume_hidden_token( tree ) 442324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 443324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 444324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 445324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Somebody (anybody) looked ahead. Note that this actually gets 446324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # triggered by both peek and look calls. The debugger will want to know 447324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # which Token object was examined. Like consumeToken, this indicates 448324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # what token was seen at that depth. A remote debugger cannot look 449324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # ahead into a file it doesn't have so look events must pass the token 450324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # even if the info is redundant. 451324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 452324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def look( i, tree ) 453324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 454324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 455324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 456324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The parser is going to look arbitrarily ahead; mark this location, 457324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the token stream's marker is sent in case you need it. 458324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 459324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def mark( marker ) 460324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 461324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 462324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 463324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # After an arbitrairly long look as with a cyclic DFA (or with 464324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # any backtrack), this informs the debugger that stream should be 465324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # rewound to the position associated with marker. 466324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 467324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def rewind( marker = nil ) 468324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 469324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 470324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 471324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def begin_backtrack( level ) 472324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 473324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 474324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 475324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def end_backtrack( level, successful ) 476324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 477324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 478324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 479324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def backtrack( level ) 480324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver begin_backtrack( level ) 481324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver successful = yield( self ) 482324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end_backtrack( level, successful ) 483324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 484324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 485324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # To watch a parser move through the grammar, the parser needs to 486324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # inform the debugger what line/charPos it is passing in the grammar. 487324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # For now, this does not know how to switch from one grammar to the 488324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # other and back for island grammars etc... 489324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # This should also allow breakpoints because the debugger can stop 490324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the parser whenever it hits this line/pos. 491324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 492324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def location( line, position ) 493324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 494324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 495324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 496324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # A recognition exception occurred such as NoViableAltError. I made 497324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # this a generic event so that I can alter the exception hierachy later 498324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # without having to alter all the debug objects. 499324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Upon error, the stack of enter rule/subrule must be properly unwound. 500324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If no viable alt occurs it is within an enter/exit decision, which 501324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # also must be rewound. Even the rewind for each mark must be unwount. 502324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # In the Java target this is pretty easy using try/finally, if a bit 503324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # ugly in the generated code. The rewind is generated in DFA.predict() 504324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # actually so no code needs to be generated for that. For languages 505324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # w/o this "finally" feature (C++?), the target implementor will have 506324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # to build an event stack or something. 507324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Across a socket for remote debugging, only the RecognitionError 508324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # data fields are transmitted. The token object or whatever that 509324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # caused the problem was the last object referenced by look. The 510324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # immediately preceding look event should hold the unexpected Token or 511324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # char. 512324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Here is a sample event trace for grammar: 513324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # b : C ({;}A|B) // {;} is there to prevent A|B becoming a set 514324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # | D 515324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # ; 516324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The sequence for this rule (with no viable alt in the subrule) for 517324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # input 'c c' (there are 3 tokens) is: 518324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # commence 519324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 520324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # enterRule b 521324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # location 7 1 522324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # enter decision 3 523324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 524324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # exit decision 3 525324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # enterAlt1 526324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # location 7 5 527324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 528324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # consumeToken [c/<4>,1:0] 529324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # location 7 7 530324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # enterSubRule 2 531324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # enter decision 2 532324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 533324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 534324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # recognitionError NoViableAltError 2 1 2 535324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # exit decision 2 536324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # exitSubRule 2 537324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # beginResync 538324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 539324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # consumeToken [c/<4>,1:1] 540324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look 541324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # endResync 542324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # look(-1) 543324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # exitRule b 544324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # terminate 545324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 546324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def recognition_exception( exception ) 547324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 548324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 549324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 550324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Indicates the recognizer is about to consume tokens to resynchronize 551324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the parser. Any consume events from here until the recovered event 552324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # are not part of the parse--they are dead tokens. 553324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 554324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def begin_resync() 555324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 556324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 557324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 558324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Indicates that the recognizer has finished consuming tokens in order 559324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # to resychronize. There may be multiple beginResync/endResync pairs 560324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # before the recognizer comes out of errorRecovery mode (in which 561324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # multiple errors are suppressed). This will be useful 562324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # in a gui where you want to probably grey out tokens that are consumed 563324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # but not matched to anything in grammar. Anything between 564324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # a beginResync/endResync pair was tossed out by the parser. 565324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 566324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def end_resync() 567324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 568324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 569324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 570324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def resync 571324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver begin_resync 572324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver yield( self ) 573324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end_resync 574324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 575324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 576324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # A semantic predicate was evaluate with this result and action text 577324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 578324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def semantic_predicate( result, predicate ) 579324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 580324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 581324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 582324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Announce that parsing has begun. Not technically useful except for 583324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # sending events over a socket. A GUI for example will launch a thread 584324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # to connect and communicate with a remote parser. The thread will want 585324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # to notify the GUI when a connection is made. ANTLR parsers 586324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # trigger this upon entry to the first rule (the ruleLevel is used to 587324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # figure this out). 588324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 589324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def commence( ) 590324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 591324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 592324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 593324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Parsing is over; successfully or not. Mostly useful for telling 594324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # remote debugging listeners that it's time to quit. When the rule 595324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # invocation level goes to zero at the end of a rule, we are done 596324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # parsing. 597324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 598324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def terminate( ) 599324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 600324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 601324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 602324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Input for a tree parser is an AST, but we know nothing for sure 603324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # about a node except its type and text (obtained from the adaptor). 604324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # This is the analog of the consumeToken method. Again, the ID is 605324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the hashCode usually of the node so it only works if hashCode is 606324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # not implemented. If the type is UP or DOWN, then 607324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # the ID is not really meaningful as it's fixed--there is 608324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # just one UP node and one DOWN navigation node. 609324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 610324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def consume_node( tree ) 611324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 612324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 613324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 614324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # A nil was created (even nil nodes have a unique ID... 615324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # they are not "null" per se). As of 4/28/2006, this 616324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # seems to be uniquely triggered when starting a new subtree 617324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # such as when entering a subrule in automatic mode and when 618324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # building a tree in rewrite mode. 619324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If you are receiving this event over a socket via 620324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # RemoteDebugEventSocketListener then only tree.ID is set. 621324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 622324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def flat_node( tree ) 623324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 624324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 625324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 626324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Upon syntax error, recognizers bracket the error with an error node 627324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # if they are building ASTs. 628324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 629324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def error_node( tree ) 630324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 631324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 632324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 633324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Announce a new node built from token elements such as type etc... 634324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If you are receiving this event over a socket via 635324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # RemoteDebugEventSocketListener then only tree.ID, type, text are 636324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # set. 637324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 638324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def create_node( node, token = nil ) 639324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 640324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 641324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 642324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Make a node the new root of an existing root. 643324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Note: the newRootID parameter is possibly different 644324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # than the TreeAdaptor.becomeRoot() newRoot parameter. 645324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # In our case, it will always be the result of calling 646324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # TreeAdaptor.becomeRoot() and not root_n or whatever. 647324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # The listener should assume that this event occurs 648324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # only when the current subrule (or rule) subtree is 649324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # being reset to newRootID. 650324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If you are receiving this event over a socket via 651324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # RemoteDebugEventSocketListener then only IDs are set. 652324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # @see antlr3.tree.TreeAdaptor.becomeRoot() 653324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 654324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def become_root( new_root, old_root ) 655324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 656324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 657324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 658324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Make childID a child of rootID. 659324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If you are receiving this event over a socket via 660324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # RemoteDebugEventSocketListener then only IDs are set. 661324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # @see antlr3.tree.TreeAdaptor.addChild() 662324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 663324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def add_child( root, child ) 664324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 665324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 666324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 667324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # Set the token start/stop token index for a subtree root or node. 668324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # If you are receiving this event over a socket via 669324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # RemoteDebugEventSocketListener then only tree.ID is set. 670324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 671324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def set_token_boundaries( tree, token_start_index, token_stop_index ) 672324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 673324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 674324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 675324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def examine_rule_memoization( rule ) 676324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver # do nothing 677324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 678324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 679324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver def on( event_name, &block ) 680324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver sclass = class << self; self; end 681324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver sclass.send( :define_method, event_name, &block ) 682324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver end 683324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 684324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver EVENTS = [ 685324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :add_child, :backtrack, :become_root, :begin_backtrack, 686324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :begin_resync, :commence, :consume_hidden_token, 687324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :consume_node, :consume_token, :create_node, :end_backtrack, 688324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :end_resync, :enter_alternative, :enter_decision, :enter_rule, 689324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :enter_sub_rule, :error_node, :exit_decision, :exit_rule, 690324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :exit_sub_rule, :flat_node, :location, :look, :mark, 691324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :recognition_exception, :resync, :rewind, 692324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver :semantic_predicate, :set_token_boundaries, :terminate 693324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver ].freeze 694324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruver 695324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 696324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 697324c4644fee44b9898524c09511bd33c3f12e2dfBen Gruverend 698