diff --git a/lib/lrama/grammar.rb b/lib/lrama/grammar.rb index cdba8fba7..02ee9afcb 100644 --- a/lib/lrama/grammar.rb +++ b/lib/lrama/grammar.rb @@ -9,6 +9,7 @@ require_relative "grammar/destructor" require_relative "grammar/error_token" require_relative "grammar/inline" +require_relative "grammar/node" require_relative "grammar/parameterized" require_relative "grammar/percent_code" require_relative "grammar/precedence" @@ -63,11 +64,12 @@ class Grammar # @aux: Auxiliary # @no_stdlib: bool # @locations: bool - # @define: Hash[String, String] + # @define: Hash[String, String?] # @required: bool # @union: Union # @precedences: Array[Precedence] # @start_nterm: Lrama::Lexer::Token::Base? + # @nodes: Array[Node::Base] extend Forwardable @@ -98,17 +100,19 @@ class Grammar attr_accessor :sym_to_rules #: Hash[Integer, Array[Rule]] attr_accessor :no_stdlib #: bool attr_accessor :locations #: bool - attr_accessor :define #: Hash[String, String] + attr_accessor :define #: Hash[String, String?] attr_accessor :required #: bool + attr_accessor :nodes #: Array[Node::Base] def_delegators "@symbols_resolver", :symbols, :nterms, :terms, :add_nterm, :add_term, :find_term_by_s_value, :find_symbol_by_number!, :find_symbol_by_id!, :token_to_symbol, :find_symbol_by_s_value!, :fill_symbol_number, :fill_nterm_type, :fill_printer, :fill_destructor, :fill_error_token, :sort_by_number! - # @rbs (Counter rule_counter, bool locations, Hash[String, String] define) -> void - def initialize(rule_counter, locations, define = {}) + # @rbs (Counter rule_counter, bool locations, Hash[String, String?] define) -> void + def initialize(rule_counter, midrule_action_counter, locations, define = {}) @rule_counter = rule_counter + @midrule_action_counter = midrule_action_counter # Code defined by "%code" @percent_codes = [] @@ -133,10 +137,16 @@ def initialize(rule_counter, locations, define = {}) @required = false @precedences = [] @start_nterm = nil + @nodes = nil append_special_symbols end + # @rbs () -> void + def evaluate_nodes + _evaluate_nodes + end + # @rbs (Counter rule_counter, Counter midrule_action_counter) -> RuleBuilder def create_rule_builder(rule_counter, midrule_action_counter) RuleBuilder.new(rule_counter, midrule_action_counter, @parameterized_resolver) @@ -162,7 +172,7 @@ def add_error_token(ident_or_tags:, token_code:, lineno:) @error_tokens << ErrorToken.new(ident_or_tags: ident_or_tags, token_code: token_code, lineno: lineno) end - # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> Array[Type] + # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> Array[Type] def add_type(id:, tag:) @types << Type.new(id: id, tag: tag) end @@ -306,6 +316,186 @@ def ielr_defined? private + # @rbs () -> void + def _evaluate_nodes + @nodes.each do |node| + case node + when Node::DefineDecl + self.define[node.variable] = node.value + when Node::ExpectDecl + self.expect = node.number + when Node::PrologueDecl + self.prologue_first_lineno = node.location.first_line + self.prologue = node.code.s_value + when Node::EpilogueDecl + self.epilogue_first_lineno = node.location.first_line + 1 + self.epilogue = node.code.s_value + when Node::RequireDecl + @required = true + when Node::LexParamDecl + node.params.each do |param| + self.lex_param = Grammar::Code::NoReferenceCode.new(type: :lex_param, token_code: param).token_code.s_value + end + when Node::ParseParamDecl + node.params.each do |param| + self.parse_param = Grammar::Code::NoReferenceCode.new(type: :parse_param, token_code: param).token_code.s_value + end + when Node::UnionDecl + self.set_union( + Grammar::Code::NoReferenceCode.new(type: :union, token_code: node.code), + node.loc.first_line + ) + when Node::DestructorDecl + self.add_destructor( + ident_or_tags: node.ident_or_tags, + token_code: node.code, + lineno: node.location.first_line + ) + when Node::PrinterDecl + self.add_printer( + ident_or_tags: node.ident_or_tags, + token_code: node.code, + lineno: node.location.first_line + ) + when Node::ErrorTokenDecl + self.add_error_token( + ident_or_tags: node.ident_or_tags, + token_code: node.code, + lineno: node.location.first_line + ) + when Node::StartDecl + self.set_start_nterm(node.id) + when Node::CodeDecl + add_percent_code(id: node.id, code: node.code) + when Node::InitialActionDecl + self.initial_action = Grammar::Code::InitialActionCode.new(type: :initial_action, token_code: node.code) + when Node::NoStdlibDecl + self.no_stdlib = true + when Node::LocationsDecl + self.locations = true + when Node::AfterShiftDecl + self.after_shift = node.id + when Node::BeforeReduceDecl + self.before_reduce = node.id + when Node::AfterReduceDecl + self.after_reduce = node.id + when Node::AfterShiftErrorTokenDecl + self.after_shift_error_token = node.id + when Node::AfterPopStackDecl + self.after_pop_stack = node.id + when Node::TokenDecl + node.tokens.each do |token| + add_term(id: token.id, alias_name: token.alias_name, token_id: token.token_id, tag: token.tag, replace: true) + end + when Node::TypeDecl + node.symbols.each do |sym| + add_type(id: sym.id, tag: sym.tag) + end + when Node::NtermDecl + node.symbols.each do |sym| + if find_term_by_s_value(sym.id.s_value) + raise ParseError, sym.id.location.generate_error_message("symbol #{sym.id.s_value} redeclared as a nonterminal") # steep:ignore UnknownConstant + else + add_type(id: sym.id, tag: sym.tag) + end + end + when Node::PrecedenceDecl + node.tokens.each do |token| + sym = add_term(id: token.id, tag: token.tag) + + case node.type + when :left + add_left(sym, node.number, token.id.s_value, token.loc.first_line) + when :right + add_right(sym, node.number, token.id.s_value, token.loc.first_line) + when :precedence + add_precedence(sym, node.number, token.id.s_value, token.loc.first_line) + when :nonassoc + add_nonassoc(sym, node.number, token.id.s_value, token.loc.first_line) + else + raise "Unknown precedence type: #{node.type}, Node: #{node}" + end + end + when Node::Rule + builder = create_rule_builder(@rule_counter, @midrule_action_counter) + builder.line = (node.rhs.first || node).location.first_line + lhs = node.id + lhs.alias_name = node.alias_name + builder.lhs = lhs + + node.rhs.each do |rhs_node| + case rhs_node + when Node::RuleRhs::Empty + builder.line = rhs_node.location.first_line + builder.add_rhs(Lrama::Lexer::Token::Empty.new(location: rhs_node.location)) + when Node::RuleRhs::Symbol + token = rhs_node.token + token.alias_name = rhs_node.alias_name + builder.add_rhs(token) + when Node::RuleRhs::InstantiateRule + token = Lrama::Lexer::Token::InstantiateRule.new( + s_value: rhs_node.s_value, alias_name: rhs_node.alias_name, + args: rhs_node.args, lhs_tag: rhs_node.lhs_tag, + location: rhs_node.location + ) + builder.add_rhs(token) + builder.line = rhs_node.location.first_line + when Node::RuleRhs::Action + user_code = rhs_node.code + user_code.alias_name = rhs_node.alias_name + user_code.tag = rhs_node.tag + builder.user_code = user_code + when Node::RuleRhs::Prec + sym = find_symbol_by_id!(rhs_node.token) + builder.precedence_sym = sym + else + raise "Unknown Node: #{rhs_node}" + end + end + + builder.complete_input + add_rule_builder(builder) + when Grammar::Node::ParameterizedRule + rhs_list = node.rhs_list.map do |rhs| + builder = Grammar::Parameterized::Rhs.new + + rhs.each do |rhs_node| + case rhs_node + when Node::RuleRhs::Empty + when Node::RuleRhs::Symbol + token = rhs_node.token + token.alias_name = rhs_node.alias_name + builder.symbols << token + when Node::RuleRhs::InstantiateRule + token = Lrama::Lexer::Token::InstantiateRule.new( + s_value: rhs_node.s_value, alias_name: rhs_node.alias_name, + args: rhs_node.args, lhs_tag: rhs_node.lhs_tag, + location: rhs_node.location + ) + builder.symbols << token + when Node::RuleRhs::Action + user_code = rhs_node.code + user_code.alias_name = rhs_node.alias_name + builder.user_code = user_code + when Node::RuleRhs::Prec + sym = find_symbol_by_id!(rhs_node.token) + builder.precedence_sym = sym + else + raise "Unknown Node: #{rhs_node}" + end + end + + builder + end + + rule = Grammar::Parameterized::Rule.new(node.name, node.parameters, rhs_list, tag: node.tag, is_inline: node.is_inline) + add_parameterized_rule(rule) + else + raise "Unknown Node: #{node}" + end + end + end + # @rbs () -> void def sort_precedence @precedences.sort_by! do |prec| diff --git a/lib/lrama/grammar/node.rb b/lib/lrama/grammar/node.rb new file mode 100644 index 000000000..8166755e5 --- /dev/null +++ b/lib/lrama/grammar/node.rb @@ -0,0 +1,34 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +require_relative "node/base" +require_relative "node/after_pop_stack_decl" +require_relative "node/after_reduce_decl" +require_relative "node/after_shift_decl" +require_relative "node/after_shift_error_token_decl" +require_relative "node/before_reduce_decl" +require_relative "node/code_decl" +require_relative "node/define_decl" +require_relative "node/destructor_decl" +require_relative "node/epilogue_decl" +require_relative "node/error_token_decl" +require_relative "node/expect_decl" +require_relative "node/initial_action_decl" +require_relative "node/lex_param_decl" +require_relative "node/locations_decl" +require_relative "node/no_stdlib_decl" +require_relative "node/nterm_decl" +require_relative "node/parameterized_rule" +require_relative "node/parse_param_decl" +require_relative "node/precedence_decl" +require_relative "node/printer_decl" +require_relative "node/prologue_decl" +require_relative "node/require_decl" +require_relative "node/rule" +require_relative "node/rule_rhs" +require_relative "node/start_decl" +require_relative "node/symbol" +require_relative "node/token" +require_relative "node/token_decl" +require_relative "node/type_decl" +require_relative "node/union_decl" diff --git a/lib/lrama/grammar/node/after_pop_stack_decl.rb b/lib/lrama/grammar/node/after_pop_stack_decl.rb new file mode 100644 index 000000000..70b60f57c --- /dev/null +++ b/lib/lrama/grammar/node/after_pop_stack_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class AfterPopStackDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/after_reduce_decl.rb b/lib/lrama/grammar/node/after_reduce_decl.rb new file mode 100644 index 000000000..1c1c61d80 --- /dev/null +++ b/lib/lrama/grammar/node/after_reduce_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class AfterReduceDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/after_shift_decl.rb b/lib/lrama/grammar/node/after_shift_decl.rb new file mode 100644 index 000000000..bbe70697e --- /dev/null +++ b/lib/lrama/grammar/node/after_shift_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class AfterShiftDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/after_shift_error_token_decl.rb b/lib/lrama/grammar/node/after_shift_error_token_decl.rb new file mode 100644 index 000000000..632dce81d --- /dev/null +++ b/lib/lrama/grammar/node/after_shift_error_token_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class AfterShiftErrorTokenDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/base.rb b/lib/lrama/grammar/node/base.rb new file mode 100644 index 000000000..d3049b3b9 --- /dev/null +++ b/lib/lrama/grammar/node/base.rb @@ -0,0 +1,19 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class Base + attr_reader :location #: Lexer::Location + + # @rbs (location: Lexer::Location) -> void + def initialize(location:) + @location = location + end + + alias :loc :location + end + end + end +end diff --git a/lib/lrama/grammar/node/before_reduce_decl.rb b/lib/lrama/grammar/node/before_reduce_decl.rb new file mode 100644 index 000000000..c88b25803 --- /dev/null +++ b/lib/lrama/grammar/node/before_reduce_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class BeforeReduceDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/code_decl.rb b/lib/lrama/grammar/node/code_decl.rb new file mode 100644 index 000000000..ad6d4bd91 --- /dev/null +++ b/lib/lrama/grammar/node/code_decl.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class CodeDecl < Base + attr_reader :id #: Lexer::Token::Ident + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (id: Lexer::Token::Ident, code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(id:, code:, location:) + @id = id + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/define_decl.rb b/lib/lrama/grammar/node/define_decl.rb new file mode 100644 index 000000000..fe80a36e5 --- /dev/null +++ b/lib/lrama/grammar/node/define_decl.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class DefineDecl < Base + attr_reader :variable #: String + attr_reader :value #: String? + + # @rbs (variable: String, value: String?, location: Lexer::Location) -> void + def initialize(variable: ,value:, location:) + @variable = variable + @value = value + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/destructor_decl.rb b/lib/lrama/grammar/node/destructor_decl.rb new file mode 100644 index 000000000..9f0653268 --- /dev/null +++ b/lib/lrama/grammar/node/destructor_decl.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class DestructorDecl < Base + attr_reader :ident_or_tags #: Array[Lexer::Token::Ident | Lexer::Token::Tag] + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(ident_or_tags:, code:, location:) + @ident_or_tags = ident_or_tags + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/epilogue_decl.rb b/lib/lrama/grammar/node/epilogue_decl.rb new file mode 100644 index 000000000..c73c59577 --- /dev/null +++ b/lib/lrama/grammar/node/epilogue_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class EpilogueDecl < Base + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(code:, location:) + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/error_token_decl.rb b/lib/lrama/grammar/node/error_token_decl.rb new file mode 100644 index 000000000..d6fc20d26 --- /dev/null +++ b/lib/lrama/grammar/node/error_token_decl.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class ErrorTokenDecl < Base + attr_reader :ident_or_tags #: Array[Lexer::Token::Ident | Lexer::Token::Tag] + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(ident_or_tags:, code:, location:) + @ident_or_tags = ident_or_tags + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/expect_decl.rb b/lib/lrama/grammar/node/expect_decl.rb new file mode 100644 index 000000000..195ee9b80 --- /dev/null +++ b/lib/lrama/grammar/node/expect_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class ExpectDecl < Base + attr_reader :number #: Integer + + # @rbs (number: Integer, location: Lexer::Location) -> void + def initialize(number:, location:) + @number = number + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/initial_action_decl.rb b/lib/lrama/grammar/node/initial_action_decl.rb new file mode 100644 index 000000000..c99ccd51f --- /dev/null +++ b/lib/lrama/grammar/node/initial_action_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class InitialActionDecl < Base + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(code:, location:) + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/lex_param_decl.rb b/lib/lrama/grammar/node/lex_param_decl.rb new file mode 100644 index 000000000..62f776f87 --- /dev/null +++ b/lib/lrama/grammar/node/lex_param_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class LexParamDecl < Base + attr_reader :params #: Array[Lexer::Token::UserCode] + + # @rbs (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + def initialize(params:, location:) + @params = params + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/locations_decl.rb b/lib/lrama/grammar/node/locations_decl.rb new file mode 100644 index 000000000..1b6510116 --- /dev/null +++ b/lib/lrama/grammar/node/locations_decl.rb @@ -0,0 +1,11 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class LocationsDecl < Base + end + end + end +end diff --git a/lib/lrama/grammar/node/no_stdlib_decl.rb b/lib/lrama/grammar/node/no_stdlib_decl.rb new file mode 100644 index 000000000..7c73f5d46 --- /dev/null +++ b/lib/lrama/grammar/node/no_stdlib_decl.rb @@ -0,0 +1,11 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class NoStdlibDecl < Base + end + end + end +end diff --git a/lib/lrama/grammar/node/nterm_decl.rb b/lib/lrama/grammar/node/nterm_decl.rb new file mode 100644 index 000000000..bbac9124c --- /dev/null +++ b/lib/lrama/grammar/node/nterm_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class NtermDecl < Base + attr_reader :symbols #: Array[Node::Symbol] + + # @rbs (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + def initialize(symbols:, location:) + @symbols = symbols + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/parameterized_rule.rb b/lib/lrama/grammar/node/parameterized_rule.rb new file mode 100644 index 000000000..8b23c5f89 --- /dev/null +++ b/lib/lrama/grammar/node/parameterized_rule.rb @@ -0,0 +1,26 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class ParameterizedRule < Base + attr_reader :name #: String + attr_reader :parameters #: Array[Lexer::Token::Base] + attr_reader :tag #: Lexer::Token::Tag? + attr_reader :rhs_list #: Array[Array[Node::Base]] + attr_reader :is_inline #: bool + + # @rbs (name: String, parameters: Array[Lexer::Token::Base], ?tag: Lexer::Token::Tag?, rhs_list: Array[Array[Node::Base]], is_inline: bool, location: Lexer::Location) -> void + def initialize(name:, parameters:, tag: nil, rhs_list:, is_inline:, location:) + @name = name + @parameters = parameters + @tag = tag + @rhs_list = rhs_list + @is_inline = is_inline + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/parse_param_decl.rb b/lib/lrama/grammar/node/parse_param_decl.rb new file mode 100644 index 000000000..d6cd0a1b6 --- /dev/null +++ b/lib/lrama/grammar/node/parse_param_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class ParseParamDecl < Base + attr_reader :params #: Array[Lexer::Token::UserCode] + + # @rbs (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + def initialize(params:, location:) + @params = params + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/precedence_decl.rb b/lib/lrama/grammar/node/precedence_decl.rb new file mode 100644 index 000000000..2cbaa4886 --- /dev/null +++ b/lib/lrama/grammar/node/precedence_decl.rb @@ -0,0 +1,25 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class PrecedenceDecl < Base + # @rbs! + # type type_enum = :left | :right | :precedence | :nonassoc + + attr_reader :type #: type_enum + attr_reader :tokens #: Array[Node::Token] + attr_reader :number #: Integer + + # @rbs (type: type_enum, tokens: Array[Node::Token], number: Integer, location: Lexer::Location) -> void + def initialize(type:, tokens:, number:, location:) + @type = type + @tokens = tokens + @number = number + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/printer_decl.rb b/lib/lrama/grammar/node/printer_decl.rb new file mode 100644 index 000000000..2a1597ecb --- /dev/null +++ b/lib/lrama/grammar/node/printer_decl.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class PrinterDecl < Base + attr_reader :ident_or_tags #: Array[Lexer::Token::Ident | Lexer::Token::Tag] + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(ident_or_tags:, code:, location:) + @ident_or_tags = ident_or_tags + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/prologue_decl.rb b/lib/lrama/grammar/node/prologue_decl.rb new file mode 100644 index 000000000..361f60ef5 --- /dev/null +++ b/lib/lrama/grammar/node/prologue_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class PrologueDecl < Base + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(code:, location:) + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/require_decl.rb b/lib/lrama/grammar/node/require_decl.rb new file mode 100644 index 000000000..61feb5006 --- /dev/null +++ b/lib/lrama/grammar/node/require_decl.rb @@ -0,0 +1,11 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class RequireDecl < Base + end + end + end +end diff --git a/lib/lrama/grammar/node/rule.rb b/lib/lrama/grammar/node/rule.rb new file mode 100644 index 000000000..d83f3c3fb --- /dev/null +++ b/lib/lrama/grammar/node/rule.rb @@ -0,0 +1,22 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class Rule < Base + attr_reader :id #: Lexer::Token::Base + attr_reader :alias_name #: String? + attr_reader :rhs #: Array[Node::Base] + + # @rbs (id: Lexer::Token::Base, ?alias_name: String?, rhs: Array[Node::Base], location: Lexer::Location) -> void + def initialize(id:, alias_name: nil, rhs:, location:) + @id = id + @alias_name = alias_name + @rhs = rhs + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs.rb b/lib/lrama/grammar/node/rule_rhs.rb new file mode 100644 index 000000000..f93cf9cac --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs.rb @@ -0,0 +1,17 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +require_relative "rule_rhs/action" +require_relative "rule_rhs/empty" +require_relative "rule_rhs/instantiate_rule" +require_relative "rule_rhs/prec" +require_relative "rule_rhs/symbol" + +module Lrama + class Grammar + module Node + module RuleRhs + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs/action.rb b/lib/lrama/grammar/node/rule_rhs/action.rb new file mode 100644 index 000000000..c5d28fc85 --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs/action.rb @@ -0,0 +1,24 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + module RuleRhs + class Action < Node::Base + attr_reader :code #: Lexer::Token::UserCode + attr_reader :alias_name #: String? + attr_reader :tag #: Lexer::Token::Tag? + + # @rbs (code: Lexer::Token::UserCode, ?alias_name: String?, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize(code:, alias_name: nil, tag: nil, location:) + @code = code + @alias_name = alias_name + @tag = tag + super(location: location) + end + end + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs/empty.rb b/lib/lrama/grammar/node/rule_rhs/empty.rb new file mode 100644 index 000000000..321a98563 --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs/empty.rb @@ -0,0 +1,13 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + module RuleRhs + class Empty < Node::Base + end + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs/instantiate_rule.rb b/lib/lrama/grammar/node/rule_rhs/instantiate_rule.rb new file mode 100644 index 000000000..fca74c4d5 --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs/instantiate_rule.rb @@ -0,0 +1,26 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + module RuleRhs + class InstantiateRule < Node::Base + attr_reader :s_value #: String + attr_reader :args #: Array[Lexer::Token::Base] + attr_reader :alias_name #: String? + attr_reader :lhs_tag #: Lexer::Token::Tag? + + # @rbs (s_value: String, args: Array[Lexer::Token::Base], ?alias_name: String?, ?lhs_tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize(s_value:, args:, alias_name: nil, lhs_tag: nil, location:) + @s_value = s_value + @args = args + @alias_name = alias_name + @lhs_tag = lhs_tag + super(location: location) + end + end + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs/prec.rb b/lib/lrama/grammar/node/rule_rhs/prec.rb new file mode 100644 index 000000000..6aa4996dd --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs/prec.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + module RuleRhs + class Prec < Node::Base + attr_reader :token #: Lexer::Token::Base + + # @rbs (token: Lexer::Token::Base, location: Lexer::Location) -> void + def initialize(token:, location:) + @token = token + super(location: location) + end + end + end + end + end +end diff --git a/lib/lrama/grammar/node/rule_rhs/symbol.rb b/lib/lrama/grammar/node/rule_rhs/symbol.rb new file mode 100644 index 000000000..945c98c09 --- /dev/null +++ b/lib/lrama/grammar/node/rule_rhs/symbol.rb @@ -0,0 +1,27 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + module RuleRhs + class Symbol < Node::Base + attr_reader :token #: Lexer::Token::Base + attr_reader :alias_name #: String? + + # @rbs (token: Lexer::Token::Base, ?alias_name: String?, location: Lexer::Location) -> void + def initialize(token:, alias_name: nil, location:) + @token = token + @alias_name = alias_name + super(location: location) + end + + # @rbs () -> String + def s_value + @token.s_value + end + end + end + end + end +end diff --git a/lib/lrama/grammar/node/start_decl.rb b/lib/lrama/grammar/node/start_decl.rb new file mode 100644 index 000000000..40801a801 --- /dev/null +++ b/lib/lrama/grammar/node/start_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class StartDecl < Base + attr_reader :id #: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize(id:, location:) + @id = id + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/symbol.rb b/lib/lrama/grammar/node/symbol.rb new file mode 100644 index 000000000..f29855d81 --- /dev/null +++ b/lib/lrama/grammar/node/symbol.rb @@ -0,0 +1,20 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class Symbol < Base + attr_reader :id #: Lexer::Token::Base + attr_accessor :tag #: Lexer::Token::Tag? + + # @rbs (id: Lexer::Token::Base, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize(id:, tag: nil, location:) + @id = id + @tag = tag + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/token.rb b/lib/lrama/grammar/node/token.rb new file mode 100644 index 000000000..e864a1a85 --- /dev/null +++ b/lib/lrama/grammar/node/token.rb @@ -0,0 +1,24 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class Token < Base + attr_reader :id #: Lexer::Token::Base + attr_reader :token_id #: Integer? + attr_reader :alias_name #: String? + attr_accessor :tag #: Lexer::Token::Tag? + + # @rbs (id: Lexer::Token::Base, ?token_id: Integer?, ?alias_name: String?, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize(id:, token_id: nil, alias_name: nil, tag: nil, location:) + @id = id + @token_id = token_id + @alias_name = alias_name + @tag = tag + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/token_decl.rb b/lib/lrama/grammar/node/token_decl.rb new file mode 100644 index 000000000..10fe9e1d5 --- /dev/null +++ b/lib/lrama/grammar/node/token_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class TokenDecl < Base + attr_reader :tokens #: Array[Node::Token] + + # @rbs (tokens: Array[Node::Token], location: Lexer::Location) -> void + def initialize(tokens:, location:) + @tokens = tokens + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/type_decl.rb b/lib/lrama/grammar/node/type_decl.rb new file mode 100644 index 000000000..ddc87bd56 --- /dev/null +++ b/lib/lrama/grammar/node/type_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class TypeDecl < Base + attr_reader :symbols #: Array[Node::Symbol] + + # @rbs (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + def initialize(symbols:, location:) + @symbols = symbols + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/node/union_decl.rb b/lib/lrama/grammar/node/union_decl.rb new file mode 100644 index 000000000..d52222bb1 --- /dev/null +++ b/lib/lrama/grammar/node/union_decl.rb @@ -0,0 +1,18 @@ +# rbs_inline: enabled +# frozen_string_literal: true + +module Lrama + class Grammar + module Node + class UnionDecl < Base + attr_reader :code #: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize(code:, location:) + @code = code + super(location: location) + end + end + end + end +end diff --git a/lib/lrama/grammar/symbols/resolver.rb b/lib/lrama/grammar/symbols/resolver.rb index ffa049832..77c98f2ea 100644 --- a/lib/lrama/grammar/symbols/resolver.rb +++ b/lib/lrama/grammar/symbols/resolver.rb @@ -16,6 +16,7 @@ class Resolver # def find_symbol_by_number!: (Integer number) -> Grammar::Symbol # def find_symbol_by_id!: (Lexer::Token::Base id) -> Grammar::Symbol # def token_to_symbol: (Lexer::Token::Base token) -> Grammar::Symbol + # def find_term_by_s_value: (::String s_value) -> Grammar::Symbol? # def find_symbol_by_s_value!: (::String s_value) -> Grammar::Symbol # def fill_nterm_type: (Array[Grammar::Type] types) -> void # def fill_symbol_number: () -> void diff --git a/lib/lrama/grammar/type.rb b/lib/lrama/grammar/type.rb index c63176944..c445c396c 100644 --- a/lib/lrama/grammar/type.rb +++ b/lib/lrama/grammar/type.rb @@ -10,12 +10,12 @@ class Type # # @rbs! # @id: Lexer::Token::Base - # @tag: Lexer::Token::Tag + # @tag: Lexer::Token::Tag? attr_reader :id #: Lexer::Token::Base - attr_reader :tag #: Lexer::Token::Tag + attr_reader :tag #: Lexer::Token::Tag? - # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> void + # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> void def initialize(id:, tag:) @id = id @tag = tag diff --git a/lib/lrama/lexer/token/base.rb b/lib/lrama/lexer/token/base.rb index 3df93bbc7..7ea5b3244 100644 --- a/lib/lrama/lexer/token/base.rb +++ b/lib/lrama/lexer/token/base.rb @@ -7,11 +7,11 @@ module Token class Base attr_reader :s_value #: String attr_reader :location #: Location - attr_accessor :alias_name #: String + attr_accessor :alias_name #: String? attr_accessor :referred #: bool attr_reader :errors #: Array[String] - # @rbs (s_value: String, ?alias_name: String, ?location: Location) -> void + # @rbs (s_value: String, ?alias_name: String?, ?location: Location) -> void def initialize(s_value:, alias_name: nil, location: nil) s_value.freeze @s_value = s_value @@ -20,6 +20,8 @@ def initialize(s_value:, alias_name: nil, location: nil) @errors = [] end + alias :loc :location + # @rbs () -> String def to_s "value: `#{s_value}`, location: #{location}" diff --git a/lib/lrama/lexer/token/instantiate_rule.rb b/lib/lrama/lexer/token/instantiate_rule.rb index 7051ba75a..5e2112a66 100644 --- a/lib/lrama/lexer/token/instantiate_rule.rb +++ b/lib/lrama/lexer/token/instantiate_rule.rb @@ -8,7 +8,7 @@ class InstantiateRule < Base attr_reader :args #: Array[Lexer::Token::Base] attr_reader :lhs_tag #: Lexer::Token::Tag? - # @rbs (s_value: String, ?alias_name: String, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void + # @rbs (s_value: String, ?alias_name: String?, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void def initialize(s_value:, alias_name: nil, location: nil, args: [], lhs_tag: nil) super s_value: s_value, alias_name: alias_name, location: location @args = args diff --git a/lib/lrama/lexer/token/user_code.rb b/lib/lrama/lexer/token/user_code.rb index 166f04954..1cdd37b50 100644 --- a/lib/lrama/lexer/token/user_code.rb +++ b/lib/lrama/lexer/token/user_code.rb @@ -7,7 +7,7 @@ module Lrama class Lexer module Token class UserCode < Base - attr_accessor :tag #: Lexer::Token::Tag + attr_accessor :tag #: Lexer::Token::Tag? # @rbs () -> Array[Lrama::Grammar::Reference] def references diff --git a/lib/lrama/parser.rb b/lib/lrama/parser.rb index 508d3ca98..6be3f2b9d 100644 --- a/lib/lrama/parser.rb +++ b/lib/lrama/parser.rb @@ -655,7 +655,7 @@ def token_to_str(t) module Lrama class Parser < Racc::Parser -module_eval(<<'...end parser.y/module_eval...', 'parser.y', 505) +module_eval(<<'...end parser.y/module_eval...', 'parser.y', 598) include Lrama::Tracer::Duration @@ -673,10 +673,12 @@ def parse message = "parse '#{File.basename(@path)}'" report_duration(message) do @lexer = Lrama::Lexer.new(@grammar_file) - @grammar = Lrama::Grammar.new(@rule_counter, @locations, @define) + @grammar = Lrama::Grammar.new(@rule_counter, @midrule_action_counter, @locations, @define) @precedence_number = 0 reset_precs - do_parse + nodes = do_parse + @grammar.nodes = nodes + @grammar.evaluate_nodes @grammar end end @@ -707,7 +709,10 @@ def on_error(error_token_id, error_value, value_stack) end def on_action_error(error_message, error_value) - if error_value.is_a?(Lrama::Lexer::Token::Base) + case error_value + when Lrama::Lexer::Token::Base + location = error_value.location + when Lrama::Grammar::Node::Base location = error_value.location else location = @lexer.location @@ -741,6 +746,20 @@ def end_c_declaration def raise_parse_error(error_message, location) raise ParseError, location.generate_error_message(error_message) end + +def merge_locations(*locations) + locations = locations.compact + first = locations.first + last = locations.last + + Lexer::Location.new( + grammar_file: @grammar_file, + first_line: first.first_line, + first_column: first.first_column, + last_line: last.last_line, + last_column: last.last_column + ) +end ...end parser.y/module_eval... ##### State transition tables begin ### @@ -932,7 +951,7 @@ def raise_parse_error(error_message, location) 2, 66, :_reduce_6, 0, 67, :_reduce_none, 1, 67, :_reduce_none, - 5, 59, :_reduce_none, + 5, 59, :_reduce_9, 0, 68, :_reduce_10, 0, 69, :_reduce_11, 5, 60, :_reduce_12, @@ -969,7 +988,7 @@ def raise_parse_error(error_message, location) 2, 71, :_reduce_43, 2, 71, :_reduce_44, 2, 71, :_reduce_45, - 2, 77, :_reduce_none, + 2, 77, :_reduce_46, 2, 77, :_reduce_47, 2, 77, :_reduce_48, 2, 77, :_reduce_49, @@ -1005,7 +1024,7 @@ def raise_parse_error(error_message, location) 3, 94, :_reduce_79, 0, 102, :_reduce_none, 1, 102, :_reduce_none, - 1, 90, :_reduce_82, + 1, 90, :_reduce_none, 1, 103, :_reduce_83, 2, 103, :_reduce_84, 2, 84, :_reduce_85, @@ -1272,42 +1291,42 @@ def raise_parse_error(error_message, location) # reduce 0 omitted -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_1(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_2(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_3(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_4(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_5(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 11) +module_eval(<<'.,.,', 'parser.y', 19) def _reduce_6(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result @@ -1318,9 +1337,20 @@ def _reduce_6(val, _values, result) # reduce 8 omitted -# reduce 9 omitted +module_eval(<<'.,.,', 'parser.y', 10) + def _reduce_9(val, _values, result) + ary = [] + ary.concat(val[0]) if val[0] + ary.concat(val[1]) if val[1] + ary.concat(val[3].flatten) + ary.append(val[4]) if val[4] + result = ary -module_eval(<<'.,.,', 'parser.y', 13) + result + end +.,., + +module_eval(<<'.,.,', 'parser.y', 21) def _reduce_10(val, _values, result) begin_c_declaration("%}") @@ -1328,7 +1358,7 @@ def _reduce_10(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 17) +module_eval(<<'.,.,', 'parser.y', 25) def _reduce_11(val, _values, result) end_c_declaration @@ -1336,31 +1366,30 @@ def _reduce_11(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 21) +module_eval(<<'.,.,', 'parser.y', 29) def _reduce_12(val, _values, result) - @grammar.prologue_first_lineno = val[0].first_line - @grammar.prologue = val[2].s_value + result = Grammar::Node::PrologueDecl.new(code: val[2], location: merge_locations(val[0].loc, val[4].loc)) result end .,., -module_eval(<<'.,.,', 'parser.y', 26) +module_eval(<<'.,.,', 'parser.y', 33) def _reduce_13(val, _values, result) - @grammar.required = true + result = Grammar::Node::RequireDecl.new(location: merge_locations(val[0].loc, val[1].loc)) result end .,., -module_eval(<<'.,.,', 'parser.y', 34) +module_eval(<<'.,.,', 'parser.y', 41) def _reduce_14(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 34) +module_eval(<<'.,.,', 'parser.y', 41) def _reduce_15(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result @@ -1371,39 +1400,50 @@ def _reduce_15(val, _values, result) # reduce 17 omitted -module_eval(<<'.,.,', 'parser.y', 77) +module_eval(<<'.,.,', 'parser.y', 108) def _reduce_18(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 77) +module_eval(<<'.,.,', 'parser.y', 108) def _reduce_19(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 36) +module_eval(<<'.,.,', 'parser.y', 43) def _reduce_20(val, _values, result) - @grammar.expect = val[1].s_value + result = Grammar::Node::ExpectDecl.new( + number: val[1].s_value, + location: merge_locations(val[0], val[1]) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 40) +module_eval(<<'.,.,', 'parser.y', 50) def _reduce_21(val, _values, result) - @grammar.define[val[1].s_value] = val[2]&.s_value + result = Grammar::Node::DefineDecl.new( + variable: val[1].s_value, + value: val[2]&.s_value, + location: merge_locations(val[0].loc, val[1].loc, val[2]&.loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 44) +module_eval(<<'.,.,', 'parser.y', 58) def _reduce_22(val, _values, result) - @grammar.define[val[1].s_value] = val[3]&.s_value + result = Grammar::Node::DefineDecl.new( + variable: val[1].s_value, + value: val[3]&.s_value, + location: merge_locations(val[0].loc, val[4].loc) + ) result end @@ -1411,80 +1451,93 @@ def _reduce_22(val, _values, result) # reduce 23 omitted -module_eval(<<'.,.,', 'parser.y', 49) +module_eval(<<'.,.,', 'parser.y', 67) def _reduce_24(val, _values, result) - val[1].each {|token| - @grammar.lex_param = Grammar::Code::NoReferenceCode.new(type: :lex_param, token_code: token).token_code.s_value - } + result = Grammar::Node::LexParamDecl.new( + params: val[1], + location: merge_locations(val[0].loc, val[1].last.loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 55) +module_eval(<<'.,.,', 'parser.y', 74) def _reduce_25(val, _values, result) - val[1].each {|token| - @grammar.parse_param = Grammar::Code::NoReferenceCode.new(type: :parse_param, token_code: token).token_code.s_value - } + result = Grammar::Node::ParseParamDecl.new( + params: val[1], + location: merge_locations(val[0].loc, val[1].last.loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 61) +module_eval(<<'.,.,', 'parser.y', 81) def _reduce_26(val, _values, result) - @grammar.add_percent_code(id: val[1], code: val[2]) + result = Grammar::Node::CodeDecl.new( + id: val[1], + code: val[2], + location: merge_locations(val[0].loc, val[2].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 65) +module_eval(<<'.,.,', 'parser.y', 89) def _reduce_27(val, _values, result) - @grammar.initial_action = Grammar::Code::InitialActionCode.new(type: :initial_action, token_code: val[1]) + result = Grammar::Node::InitialActionDecl.new( + code: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 69) +module_eval(<<'.,.,', 'parser.y', 96) def _reduce_28(val, _values, result) - @grammar.no_stdlib = true + result = Grammar::Node::NoStdlibDecl.new( + location: val[0].loc + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 73) +module_eval(<<'.,.,', 'parser.y', 102) def _reduce_29(val, _values, result) - @grammar.locations = true + result = Grammar::Node::LocationsDecl.new( + location: val[0].loc + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 133) +module_eval(<<'.,.,', 'parser.y', 179) def _reduce_30(val, _values, result) result = val result end .,., -module_eval(<<'.,.,', 'parser.y', 133) +module_eval(<<'.,.,', 'parser.y', 179) def _reduce_31(val, _values, result) result = val result end .,., -module_eval(<<'.,.,', 'parser.y', 133) +module_eval(<<'.,.,', 'parser.y', 179) def _reduce_32(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 133) +module_eval(<<'.,.,', 'parser.y', 179) def _reduce_33(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result @@ -1497,182 +1550,192 @@ def _reduce_33(val, _values, result) # reduce 36 omitted -module_eval(<<'.,.,', 'parser.y', 82) +module_eval(<<'.,.,', 'parser.y', 113) def _reduce_37(val, _values, result) - @grammar.set_union( - Grammar::Code::NoReferenceCode.new(type: :union, token_code: val[1]), - val[1].line + result = Grammar::Node::UnionDecl.new( + code: val[1], + location: val[1].loc ) result end .,., -module_eval(<<'.,.,', 'parser.y', 89) +module_eval(<<'.,.,', 'parser.y', 120) def _reduce_38(val, _values, result) - @grammar.add_destructor( + result = Grammar::Node::DestructorDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) result end .,., -module_eval(<<'.,.,', 'parser.y', 97) +module_eval(<<'.,.,', 'parser.y', 128) def _reduce_39(val, _values, result) - @grammar.add_printer( + result = Grammar::Node::PrinterDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) result end .,., -module_eval(<<'.,.,', 'parser.y', 105) +module_eval(<<'.,.,', 'parser.y', 136) def _reduce_40(val, _values, result) - @grammar.add_error_token( + result = Grammar::Node::ErrorTokenDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) result end .,., -module_eval(<<'.,.,', 'parser.y', 113) +module_eval(<<'.,.,', 'parser.y', 144) def _reduce_41(val, _values, result) - @grammar.after_shift = val[1] + result = Grammar::Node::AfterShiftDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 117) +module_eval(<<'.,.,', 'parser.y', 151) def _reduce_42(val, _values, result) - @grammar.before_reduce = val[1] + result = Grammar::Node::BeforeReduceDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 121) +module_eval(<<'.,.,', 'parser.y', 158) def _reduce_43(val, _values, result) - @grammar.after_reduce = val[1] + result = Grammar::Node::AfterReduceDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 125) +module_eval(<<'.,.,', 'parser.y', 165) def _reduce_44(val, _values, result) - @grammar.after_shift_error_token = val[1] + result = Grammar::Node::AfterShiftErrorTokenDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 129) +module_eval(<<'.,.,', 'parser.y', 172) def _reduce_45(val, _values, result) - @grammar.after_pop_stack = val[1] + result = Grammar::Node::AfterPopStackDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end .,., -# reduce 46 omitted +module_eval(<<'.,.,', 'parser.y', 181) + def _reduce_46(val, _values, result) + result = Grammar::Node::TokenDecl.new(tokens: val[1], location: merge_locations(val[0].loc, val[1].last.loc)) -module_eval(<<'.,.,', 'parser.y', 136) + result + end +.,., + +module_eval(<<'.,.,', 'parser.y', 185) def _reduce_47(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - @grammar.add_type(id: id, tag: hash[:tag]) - } - } + result = Grammar::Node::TypeDecl.new( + symbols: val[1], + location: merge_locations(*val[1].map(&:loc)) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 144) +module_eval(<<'.,.,', 'parser.y', 192) def _reduce_48(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - if @grammar.find_term_by_s_value(id.s_value) - on_action_error("symbol #{id.s_value} redeclared as a nonterminal", id) - else - @grammar.add_type(id: id, tag: hash[:tag]) - end - } - } + result = Grammar::Node::NtermDecl.new( + symbols: val[1], + location: merge_locations(*val[1].map(&:loc)) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 156) +module_eval(<<'.,.,', 'parser.y', 199) def _reduce_49(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_left(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :left, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 result end .,., -module_eval(<<'.,.,', 'parser.y', 166) +module_eval(<<'.,.,', 'parser.y', 207) def _reduce_50(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_right(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :right, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 result end .,., -module_eval(<<'.,.,', 'parser.y', 176) +module_eval(<<'.,.,', 'parser.y', 215) def _reduce_51(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_precedence(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :precedence, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 result end .,., -module_eval(<<'.,.,', 'parser.y', 186) +module_eval(<<'.,.,', 'parser.y', 223) def _reduce_52(val, _values, result) - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_nonassoc(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :nonassoc, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 result end .,., -module_eval(<<'.,.,', 'parser.y', 196) +module_eval(<<'.,.,', 'parser.y', 231) def _reduce_53(val, _values, result) - @grammar.set_start_nterm(val[1]) + result = Grammar::Node::StartDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) result end @@ -1682,35 +1745,37 @@ def _reduce_53(val, _values, result) # reduce 55 omitted -module_eval(<<'.,.,', 'parser.y', 214) +module_eval(<<'.,.,', 'parser.y', 254) def _reduce_56(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 214) +module_eval(<<'.,.,', 'parser.y', 254) def _reduce_57(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 202) +module_eval(<<'.,.,', 'parser.y', 240) def _reduce_58(val, _values, result) - val[1].each {|token_declaration| - @grammar.add_term(id: token_declaration[0], alias_name: token_declaration[2], token_id: token_declaration[1]&.s_value, tag: val[0], replace: true) + val[1].each {|token| + token.tag = val[0] } + result = val[1] result end .,., -module_eval(<<'.,.,', 'parser.y', 208) +module_eval(<<'.,.,', 'parser.y', 247) def _reduce_59(val, _values, result) - val[2].each {|token_declaration| - @grammar.add_term(id: token_declaration[0], alias_name: token_declaration[2], token_id: token_declaration[1]&.s_value, tag: val[1], replace: true) + val[2].each {|token| + token.tag = val[1] } + result = val[0].concat(val[2]) result end @@ -1720,67 +1785,78 @@ def _reduce_59(val, _values, result) # reduce 61 omitted -module_eval(<<'.,.,', 'parser.y', 213) +module_eval(<<'.,.,', 'parser.y', 255) def _reduce_62(val, _values, result) - result = val + result = Grammar::Node::Token.new( + id: val[0], token_id: val[1]&.s_value, alias_name: val[2]&.s_value, + location: merge_locations(val[0].loc, val[1]&.loc, val[2]&.loc) + ) + result end .,., -module_eval(<<'.,.,', 'parser.y', 218) +module_eval(<<'.,.,', 'parser.y', 264) def _reduce_63(val, _values, result) - rule = Grammar::Parameterized::Rule.new(val[1].s_value, val[3], val[7], tag: val[5]) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[1].s_value, parameters: val[3], tag: val[5], + rhs_list: val[7], is_inline: false, + location: merge_locations(val[0].loc, val[6].loc, *val[7].flatten.map(&:loc)) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 225) +module_eval(<<'.,.,', 'parser.y', 274) def _reduce_64(val, _values, result) - rule = Grammar::Parameterized::Rule.new(val[2].s_value, [], val[4], is_inline: true) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[2].s_value, parameters: [], + rhs_list: val[4], is_inline: true, + location: merge_locations(val[0].loc, val[3].loc, *val[4].flatten.map(&:loc)) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 230) +module_eval(<<'.,.,', 'parser.y', 282) def _reduce_65(val, _values, result) - rule = Grammar::Parameterized::Rule.new(val[2].s_value, val[4], val[7], is_inline: true) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[2].s_value, parameters: val[4], + rhs_list: val[7], is_inline: true, + location: merge_locations(val[0].loc, val[6].loc, *val[7].flatten.map(&:loc)) + ) result end .,., -module_eval(<<'.,.,', 'parser.y', 235) +module_eval(<<'.,.,', 'parser.y', 290) def _reduce_66(val, _values, result) result = [val[0]] result end .,., -module_eval(<<'.,.,', 'parser.y', 236) +module_eval(<<'.,.,', 'parser.y', 291) def _reduce_67(val, _values, result) result = val[0].append(val[2]) result end .,., -module_eval(<<'.,.,', 'parser.y', 241) +module_eval(<<'.,.,', 'parser.y', 296) def _reduce_68(val, _values, result) - builder = val[0] - result = [builder] + result = [val[0]] result end .,., -module_eval(<<'.,.,', 'parser.y', 246) +module_eval(<<'.,.,', 'parser.y', 300) def _reduce_69(val, _values, result) - builder = val[2] - result = val[0].append(builder) + result = val[0].append(val[2]) result end @@ -1794,74 +1870,76 @@ def _reduce_69(val, _values, result) # reduce 73 omitted -module_eval(<<'.,.,', 'parser.y', 253) +module_eval(<<'.,.,', 'parser.y', 306) def _reduce_74(val, _values, result) reset_precs - result = Grammar::Parameterized::Rhs.new + result = [] result end .,., -module_eval(<<'.,.,', 'parser.y', 258) +module_eval(<<'.,.,', 'parser.y', 311) def _reduce_75(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = val[1] - token.alias_name = val[2] - builder = val[0] - builder.symbols << token - result = builder + node = Grammar::Node::RuleRhs::Symbol.new( + token: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 267) +module_eval(<<'.,.,', 'parser.y', 320) def _reduce_76(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - builder = val[0] - builder.symbols << Lrama::Lexer::Token::InstantiateRule.new(s_value: val[2], location: @lexer.location, args: [val[1]]) - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[2], args: [val[1]], + location: val[1].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 274) +module_eval(<<'.,.,', 'parser.y', 329) def _reduce_77(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - builder = val[0] - builder.symbols << Lrama::Lexer::Token::InstantiateRule.new(s_value: val[1].s_value, alias_name: val[5], location: @lexer.location, args: val[3], lhs_tag: val[6]) - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[1].s_value, args: val[3], + alias_name: val[5], lhs_tag: val[6], + location: merge_locations(val[1].loc, val[4], val[6]&.loc) + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 281) +module_eval(<<'.,.,', 'parser.y', 339) def _reduce_78(val, _values, result) - user_code = val[1] - user_code.alias_name = val[2] - builder = val[0] - builder.user_code = user_code - result = builder + node = Grammar::Node::RuleRhs::Action.new( + code: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 289) +module_eval(<<'.,.,', 'parser.y', 347) def _reduce_79(val, _values, result) on_action_error("multiple %prec in a rule", val[0]) if prec_seen? - sym = @grammar.find_symbol_by_id!(val[2]) - if val[0].rhs.empty? - @opening_prec_seen = true - else - @trailing_prec_seen = true - end - builder = val[0] - builder.precedence_sym = sym - result = builder + @prec_seen = true + node = Grammar::Node::RuleRhs::Prec.new( + token: val[2], + location: val[2].loc + ) + result.append(node) result end @@ -1871,42 +1949,45 @@ def _reduce_79(val, _values, result) # reduce 81 omitted -module_eval(<<'.,.,', 'parser.y', 301) - def _reduce_82(val, _values, result) - result = val[0].s_value if val[0] - result - end -.,., +# reduce 82 omitted -module_eval(<<'.,.,', 'parser.y', 315) +module_eval(<<'.,.,', 'parser.y', 380) def _reduce_83(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 315) +module_eval(<<'.,.,', 'parser.y', 380) def _reduce_84(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 306) +module_eval(<<'.,.,', 'parser.y', 361) def _reduce_85(val, _values, result) - result = if val[0] - [{tag: val[0], tokens: val[1]}] - else - [{tag: nil, tokens: val[1]}] + result = val[1].map do |id| + Grammar::Node::Symbol.new( + id: id, tag: val[0], + location: id.loc + ) end result end .,., -module_eval(<<'.,.,', 'parser.y', 312) +module_eval(<<'.,.,', 'parser.y', 370) def _reduce_86(val, _values, result) - result = val[0].append({tag: val[1], tokens: val[2]}) + syms = val[2].map do |id| + Grammar::Node::Symbol.new( + id: id, tag: val[1], + location: id.loc + ) + end + result = val[0].concat(syms) + result end .,., @@ -1915,7 +1996,7 @@ def _reduce_86(val, _values, result) # reduce 88 omitted -module_eval(<<'.,.,', 'parser.y', 321) +module_eval(<<'.,.,', 'parser.y', 386) def _reduce_89(val, _values, result) begin_c_declaration("}") @@ -1923,7 +2004,7 @@ def _reduce_89(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 325) +module_eval(<<'.,.,', 'parser.y', 390) def _reduce_90(val, _values, result) end_c_declaration @@ -1931,7 +2012,7 @@ def _reduce_90(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 329) +module_eval(<<'.,.,', 'parser.y', 394) def _reduce_91(val, _values, result) result = val[2] @@ -1939,58 +2020,86 @@ def _reduce_91(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 338) +module_eval(<<'.,.,', 'parser.y', 437) def _reduce_92(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 338) +module_eval(<<'.,.,', 'parser.y', 437) def _reduce_93(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 338) +module_eval(<<'.,.,', 'parser.y', 437) def _reduce_94(val, _values, result) result = val result end .,., -module_eval(<<'.,.,', 'parser.y', 338) +module_eval(<<'.,.,', 'parser.y', 437) def _reduce_95(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 338) +module_eval(<<'.,.,', 'parser.y', 437) def _reduce_96(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 333) +module_eval(<<'.,.,', 'parser.y', 400) def _reduce_97(val, _values, result) - result = [{tag: nil, tokens: val[0]}] + result = val[0].map do |id| + Grammar::Node::Token.new( + id: id, + location: id.loc + ) + end + result end .,., -module_eval(<<'.,.,', 'parser.y', 334) +module_eval(<<'.,.,', 'parser.y', 409) def _reduce_98(val, _values, result) - result = val[0].map {|tag, ids| {tag: tag, tokens: ids} } + result = val[0].flat_map do |tag, ids| + ids.map do |id| + Grammar::Node::Token.new( + id: id, + tag: tag, + location: id.loc + ) + end + end + result end .,., -module_eval(<<'.,.,', 'parser.y', 335) +module_eval(<<'.,.,', 'parser.y', 421) def _reduce_99(val, _values, result) - result = [{tag: nil, tokens: val[0]}, {tag: val[1], tokens: val[2]}] + # result = [{tag: nil, tokens: val[0]}, {tag: val[1], tokens: val[2]}] + result = val[0].map do |id| + Grammar::Node::Token.new( + id: id, + location: id.loc + ) + end + val[2].map do |id| + Grammar::Node::Token.new( + id: id, + tag: val[1], + location: id.loc + ) + end + result end .,., @@ -1999,14 +2108,14 @@ def _reduce_99(val, _values, result) # reduce 101 omitted -module_eval(<<'.,.,', 'parser.y', 346) +module_eval(<<'.,.,', 'parser.y', 445) def _reduce_102(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result end .,., -module_eval(<<'.,.,', 'parser.y', 346) +module_eval(<<'.,.,', 'parser.y', 445) def _reduce_103(val, _values, result) result = val[1] ? val[1].unshift(val[0]) : val result @@ -2017,153 +2126,148 @@ def _reduce_103(val, _values, result) # reduce 105 omitted -module_eval(<<'.,.,', 'parser.y', 348) +module_eval(<<'.,.,', 'parser.y', 447) def _reduce_106(val, _values, result) - lhs = val[0] - lhs.alias_name = val[1] - val[3].each do |builder| - builder.lhs = lhs - builder.complete_input - @grammar.add_rule_builder(builder) - end + result = val[3].map do |rhs| + Grammar::Node::Rule.new( + id: val[0], + alias_name: val[1], + rhs: rhs, + location: val[0].loc + ) + end result end .,., -module_eval(<<'.,.,', 'parser.y', 360) +module_eval(<<'.,.,', 'parser.y', 460) def _reduce_107(val, _values, result) - if val[0].rhs.count > 1 - empties = val[0].rhs.select { |sym| sym.is_a?(Lrama::Lexer::Token::Empty) } + if val[0].reject {|sym| sym.is_a?(Grammar::Node::RuleRhs::Action) || sym.is_a?(Grammar::Node::RuleRhs::Prec) }.count > 1 + empties = val[0].select { |sym| sym.is_a?(Grammar::Node::RuleRhs::Empty) } empties.each do |empty| on_action_error("%empty on non-empty rule", empty) end end - builder = val[0] - if !builder.line - builder.line = @lexer.line - 1 - end - result = [builder] + result = [val[0]] result end .,., -module_eval(<<'.,.,', 'parser.y', 374) +module_eval(<<'.,.,', 'parser.y', 470) def _reduce_108(val, _values, result) - builder = val[2] - if !builder.line - builder.line = @lexer.line - 1 - end - result = val[0].append(builder) + result = val[0].append(val[2]) result end .,., -module_eval(<<'.,.,', 'parser.y', 384) +module_eval(<<'.,.,', 'parser.y', 476) def _reduce_109(val, _values, result) reset_precs - result = @grammar.create_rule_builder(@rule_counter, @midrule_action_counter) + result = [] result end .,., -module_eval(<<'.,.,', 'parser.y', 389) +module_eval(<<'.,.,', 'parser.y', 481) def _reduce_110(val, _values, result) - builder = val[0] - builder.add_rhs(Lrama::Lexer::Token::Empty.new(location: @lexer.location)) - result = builder + node = Grammar::Node::RuleRhs::Empty.new(location: val[1].loc) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 395) +module_eval(<<'.,.,', 'parser.y', 486) def _reduce_111(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = val[1] - token.alias_name = val[2] - builder = val[0] - builder.add_rhs(token) - result = builder + node = Grammar::Node::RuleRhs::Symbol.new( + token: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 404) +module_eval(<<'.,.,', 'parser.y', 495) def _reduce_112(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = Lrama::Lexer::Token::InstantiateRule.new(s_value: val[2], alias_name: val[3], location: @lexer.location, args: [val[1]], lhs_tag: val[4]) - builder = val[0] - builder.add_rhs(token) - builder.line = val[1].first_line - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[2], args: [val[1]], + alias_name: val[3], lhs_tag: val[4], + location: merge_locations(val[1].loc, val[4]&.loc) + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 413) +module_eval(<<'.,.,', 'parser.y', 505) def _reduce_113(val, _values, result) on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = Lrama::Lexer::Token::InstantiateRule.new(s_value: val[1].s_value, alias_name: val[5], location: @lexer.location, args: val[3], lhs_tag: val[6]) - builder = val[0] - builder.add_rhs(token) - builder.line = val[1].first_line - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[1].s_value, args: val[3], + alias_name: val[5], lhs_tag: val[6], + location: merge_locations(val[1].loc, val[6]&.loc) + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 422) +module_eval(<<'.,.,', 'parser.y', 515) def _reduce_114(val, _values, result) - user_code = val[1] - user_code.alias_name = val[2] - user_code.tag = val[3] - builder = val[0] - builder.user_code = user_code - result = builder + node = Grammar::Node::RuleRhs::Action.new( + code: val[1], alias_name: val[2], tag: val[3], + location: val[1].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 431) +module_eval(<<'.,.,', 'parser.y', 523) def _reduce_115(val, _values, result) on_action_error("multiple %prec in a rule", val[0]) if prec_seen? - sym = @grammar.find_symbol_by_id!(val[2]) - if val[0].rhs.empty? + if val[0].empty? @opening_prec_seen = true else @trailing_prec_seen = true end - builder = val[0] - builder.precedence_sym = sym - result = builder + + node = Grammar::Node::RuleRhs::Prec.new( + token: val[2], + location: val[2].loc + ) + result.append(node) result end .,., -module_eval(<<'.,.,', 'parser.y', 444) +module_eval(<<'.,.,', 'parser.y', 538) def _reduce_116(val, _values, result) result = "option" result end .,., -module_eval(<<'.,.,', 'parser.y', 445) +module_eval(<<'.,.,', 'parser.y', 539) def _reduce_117(val, _values, result) result = "nonempty_list" result end .,., -module_eval(<<'.,.,', 'parser.y', 446) +module_eval(<<'.,.,', 'parser.y', 540) def _reduce_118(val, _values, result) result = "list" result @@ -2174,7 +2278,7 @@ def _reduce_118(val, _values, result) # reduce 120 omitted -module_eval(<<'.,.,', 'parser.y', 451) +module_eval(<<'.,.,', 'parser.y', 545) def _reduce_121(val, _values, result) result = if val[1] [Lrama::Lexer::Token::InstantiateRule.new(s_value: val[1].s_value, location: @lexer.location, args: val[0])] @@ -2186,28 +2290,28 @@ def _reduce_121(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 457) +module_eval(<<'.,.,', 'parser.y', 551) def _reduce_122(val, _values, result) result = val[0].append(val[2]) result end .,., -module_eval(<<'.,.,', 'parser.y', 458) +module_eval(<<'.,.,', 'parser.y', 552) def _reduce_123(val, _values, result) result = val[0].append(Lrama::Lexer::Token::InstantiateRule.new(s_value: val[2].s_value, location: @lexer.location, args: val[4])) result end .,., -module_eval(<<'.,.,', 'parser.y', 459) +module_eval(<<'.,.,', 'parser.y', 553) def _reduce_124(val, _values, result) result = [Lrama::Lexer::Token::InstantiateRule.new(s_value: val[0].s_value, location: @lexer.location, args: val[2])] result end .,., -module_eval(<<'.,.,', 'parser.y', 464) +module_eval(<<'.,.,', 'parser.y', 558) def _reduce_125(val, _values, result) if prec_seen? on_action_error("multiple User_code after %prec", val[0]) if @code_after_prec @@ -2219,7 +2323,7 @@ def _reduce_125(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 472) +module_eval(<<'.,.,', 'parser.y', 566) def _reduce_126(val, _values, result) end_c_declaration @@ -2227,7 +2331,7 @@ def _reduce_126(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 476) +module_eval(<<'.,.,', 'parser.y', 570) def _reduce_127(val, _values, result) result = val[2] @@ -2235,14 +2339,14 @@ def _reduce_127(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 479) +module_eval(<<'.,.,', 'parser.y', 573) def _reduce_128(val, _values, result) result = val[1].s_value result end .,., -module_eval(<<'.,.,', 'parser.y', 484) +module_eval(<<'.,.,', 'parser.y', 578) def _reduce_129(val, _values, result) begin_c_declaration('\Z') @@ -2250,11 +2354,10 @@ def _reduce_129(val, _values, result) end .,., -module_eval(<<'.,.,', 'parser.y', 488) +module_eval(<<'.,.,', 'parser.y', 582) def _reduce_130(val, _values, result) end_c_declaration - @grammar.epilogue_first_lineno = val[0].first_line + 1 - @grammar.epilogue = val[2].s_value + result = Grammar::Node::EpilogueDecl.new(code: val[2], location: merge_locations(val[0].loc, val[2].loc)) result end @@ -2270,7 +2373,7 @@ def _reduce_130(val, _values, result) # reduce 135 omitted -module_eval(<<'.,.,', 'parser.y', 500) +module_eval(<<'.,.,', 'parser.y', 593) def _reduce_136(val, _values, result) result = Lrama::Lexer::Token::Ident.new(s_value: val[0].s_value, location: val[0].location) result diff --git a/parser.y b/parser.y index 797c5a337..2250abb34 100644 --- a/parser.y +++ b/parser.y @@ -7,6 +7,14 @@ class Lrama::Parser rule input: prologue_declaration* bison_declaration* "%%" rules_or_grammar_declaration+ epilogue_declaration? + { + ary = [] + ary.concat(val[0]) if val[0] + ary.concat(val[1]) if val[1] + ary.concat(val[3].flatten) + ary.append(val[4]) if val[4] + result = ary + } prologue_declaration: "%{" @@ -19,12 +27,11 @@ rule } "%}" { - @grammar.prologue_first_lineno = val[0].first_line - @grammar.prologue = val[2].s_value + result = Grammar::Node::PrologueDecl.new(code: val[2], location: merge_locations(val[0].loc, val[4].loc)) } | "%require" STRING { - @grammar.required = true + result = Grammar::Node::RequireDecl.new(location: merge_locations(val[0].loc, val[1].loc)) } bison_declaration: @@ -34,44 +41,68 @@ rule parser_option: "%expect" INTEGER { - @grammar.expect = val[1].s_value + result = Grammar::Node::ExpectDecl.new( + number: val[1].s_value, + location: merge_locations(val[0], val[1]) + ) } | "%define" variable value { - @grammar.define[val[1].s_value] = val[2]&.s_value + result = Grammar::Node::DefineDecl.new( + variable: val[1].s_value, + value: val[2]&.s_value, + location: merge_locations(val[0].loc, val[1].loc, val[2]&.loc) + ) } | "%define" variable "{" value "}" { - @grammar.define[val[1].s_value] = val[3]&.s_value + result = Grammar::Node::DefineDecl.new( + variable: val[1].s_value, + value: val[3]&.s_value, + location: merge_locations(val[0].loc, val[4].loc) + ) } | "%param" param+ | "%lex-param" param+ { - val[1].each {|token| - @grammar.lex_param = Grammar::Code::NoReferenceCode.new(type: :lex_param, token_code: token).token_code.s_value - } + result = Grammar::Node::LexParamDecl.new( + params: val[1], + location: merge_locations(val[0].loc, val[1].last.loc) + ) } | "%parse-param" param+ { - val[1].each {|token| - @grammar.parse_param = Grammar::Code::NoReferenceCode.new(type: :parse_param, token_code: token).token_code.s_value - } + result = Grammar::Node::ParseParamDecl.new( + params: val[1], + location: merge_locations(val[0].loc, val[1].last.loc) + ) } | "%code" IDENTIFIER param { - @grammar.add_percent_code(id: val[1], code: val[2]) + result = Grammar::Node::CodeDecl.new( + id: val[1], + code: val[2], + location: merge_locations(val[0].loc, val[2].loc) + ) } | "%initial-action" param { - @grammar.initial_action = Grammar::Code::InitialActionCode.new(type: :initial_action, token_code: val[1]) + result = Grammar::Node::InitialActionDecl.new( + code: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } | "%no-stdlib" { - @grammar.no_stdlib = true + result = Grammar::Node::NoStdlibDecl.new( + location: val[0].loc + ) } | "%locations" { - @grammar.locations = true + result = Grammar::Node::LocationsDecl.new( + location: val[0].loc + ) } grammar_declaration: @@ -80,156 +111,180 @@ rule | inline_declaration | "%union" param { - @grammar.set_union( - Grammar::Code::NoReferenceCode.new(type: :union, token_code: val[1]), - val[1].line + result = Grammar::Node::UnionDecl.new( + code: val[1], + location: val[1].loc ) } | "%destructor" param (symbol | TAG)+ { - @grammar.add_destructor( + result = Grammar::Node::DestructorDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) } | "%printer" param (symbol | TAG)+ { - @grammar.add_printer( + result = Grammar::Node::PrinterDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) } | "%error-token" param (symbol | TAG)+ { - @grammar.add_error_token( + result = Grammar::Node::ErrorTokenDecl.new( ident_or_tags: val[2].flatten, - token_code: val[1], - lineno: val[1].line + code: val[1], + location: val[1].loc ) } | "%after-shift" IDENTIFIER { - @grammar.after_shift = val[1] + result = Grammar::Node::AfterShiftDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } | "%before-reduce" IDENTIFIER { - @grammar.before_reduce = val[1] + result = Grammar::Node::BeforeReduceDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } | "%after-reduce" IDENTIFIER { - @grammar.after_reduce = val[1] + result = Grammar::Node::AfterReduceDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } | "%after-shift-error-token" IDENTIFIER { - @grammar.after_shift_error_token = val[1] + result = Grammar::Node::AfterShiftErrorTokenDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } | "%after-pop-stack" IDENTIFIER { - @grammar.after_pop_stack = val[1] + result = Grammar::Node::AfterPopStackDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } symbol_declaration: "%token" token_declarations + { + result = Grammar::Node::TokenDecl.new(tokens: val[1], location: merge_locations(val[0].loc, val[1].last.loc)) + } | "%type" symbol_declarations { - val[1].each {|hash| - hash[:tokens].each {|id| - @grammar.add_type(id: id, tag: hash[:tag]) - } - } + result = Grammar::Node::TypeDecl.new( + symbols: val[1], + location: merge_locations(*val[1].map(&:loc)) + ) } | "%nterm" symbol_declarations { - val[1].each {|hash| - hash[:tokens].each {|id| - if @grammar.find_term_by_s_value(id.s_value) - on_action_error("symbol #{id.s_value} redeclared as a nonterminal", id) - else - @grammar.add_type(id: id, tag: hash[:tag]) - end - } - } + result = Grammar::Node::NtermDecl.new( + symbols: val[1], + location: merge_locations(*val[1].map(&:loc)) + ) } | "%left" token_declarations_for_precedence { - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_left(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :left, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 } | "%right" token_declarations_for_precedence { - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_right(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :right, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 } | "%precedence" token_declarations_for_precedence { - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_precedence(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :precedence, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 } | "%nonassoc" token_declarations_for_precedence { - val[1].each {|hash| - hash[:tokens].each {|id| - sym = @grammar.add_term(id: id, tag: hash[:tag]) - @grammar.add_nonassoc(sym, @precedence_number, id.s_value, id.first_line) - } - } + result = Grammar::Node::PrecedenceDecl.new( + type: :nonassoc, tokens: val[1], number: @precedence_number, + location: merge_locations(val[0].loc, val[1].last.loc) + ) @precedence_number += 1 } | "%start" IDENTIFIER { - @grammar.set_start_nterm(val[1]) + result = Grammar::Node::StartDecl.new( + id: val[1], + location: merge_locations(val[0].loc, val[1].loc) + ) } token_declarations: TAG? token_declaration+ { - val[1].each {|token_declaration| - @grammar.add_term(id: token_declaration[0], alias_name: token_declaration[2], token_id: token_declaration[1]&.s_value, tag: val[0], replace: true) + val[1].each {|token| + token.tag = val[0] } + result = val[1] } | token_declarations TAG token_declaration+ { - val[2].each {|token_declaration| - @grammar.add_term(id: token_declaration[0], alias_name: token_declaration[2], token_id: token_declaration[1]&.s_value, tag: val[1], replace: true) + val[2].each {|token| + token.tag = val[1] } + result = val[0].concat(val[2]) } - token_declaration: id INTEGER? alias { result = val } + token_declaration: id INTEGER? alias + { + result = Grammar::Node::Token.new( + id: val[0], token_id: val[1]&.s_value, alias_name: val[2]&.s_value, + location: merge_locations(val[0].loc, val[1]&.loc, val[2]&.loc) + ) + } rule_declaration: "%rule" IDENTIFIER "(" rule_args ")" TAG? ":" rule_rhs_list { - rule = Grammar::Parameterized::Rule.new(val[1].s_value, val[3], val[7], tag: val[5]) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[1].s_value, parameters: val[3], tag: val[5], + rhs_list: val[7], is_inline: false, + location: merge_locations(val[0].loc, val[6].loc, *val[7].flatten.map(&:loc)) + ) } inline_declaration: "%rule" "%inline" IDENT_COLON ":" rule_rhs_list { - rule = Grammar::Parameterized::Rule.new(val[2].s_value, [], val[4], is_inline: true) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[2].s_value, parameters: [], + rhs_list: val[4], is_inline: true, + location: merge_locations(val[0].loc, val[3].loc, *val[4].flatten.map(&:loc)) + ) } | "%rule" "%inline" IDENTIFIER "(" rule_args ")" ":" rule_rhs_list { - rule = Grammar::Parameterized::Rule.new(val[2].s_value, val[4], val[7], is_inline: true) - @grammar.add_parameterized_rule(rule) + result = Grammar::Node::ParameterizedRule.new( + name: val[2].s_value, parameters: val[4], + rhs_list: val[7], is_inline: true, + location: merge_locations(val[0].loc, val[6].loc, *val[7].flatten.map(&:loc)) + ) } rule_args: @@ -239,78 +294,88 @@ rule rule_rhs_list: rule_rhs { - builder = val[0] - result = [builder] + result = [val[0]] } | rule_rhs_list "|" rule_rhs { - builder = val[2] - result = val[0].append(builder) + result = val[0].append(val[2]) } rule_rhs: "%empty"? { reset_precs - result = Grammar::Parameterized::Rhs.new + result = [] } | rule_rhs symbol named_ref? { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = val[1] - token.alias_name = val[2] - builder = val[0] - builder.symbols << token - result = builder + node = Grammar::Node::RuleRhs::Symbol.new( + token: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) } | rule_rhs symbol parameterized_suffix { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - builder = val[0] - builder.symbols << Lrama::Lexer::Token::InstantiateRule.new(s_value: val[2], location: @lexer.location, args: [val[1]]) - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[2], args: [val[1]], + location: val[1].loc + ) + result.append(node) } | rule_rhs IDENTIFIER "(" parameterized_args ")" named_ref? TAG? { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - builder = val[0] - builder.symbols << Lrama::Lexer::Token::InstantiateRule.new(s_value: val[1].s_value, alias_name: val[5], location: @lexer.location, args: val[3], lhs_tag: val[6]) - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[1].s_value, args: val[3], + alias_name: val[5], lhs_tag: val[6], + location: merge_locations(val[1].loc, val[4], val[6]&.loc) + ) + result.append(node) } | rule_rhs action named_ref? { - user_code = val[1] - user_code.alias_name = val[2] - builder = val[0] - builder.user_code = user_code - result = builder + node = Grammar::Node::RuleRhs::Action.new( + code: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) } | rule_rhs "%prec" symbol { on_action_error("multiple %prec in a rule", val[0]) if prec_seen? - sym = @grammar.find_symbol_by_id!(val[2]) - if val[0].rhs.empty? - @opening_prec_seen = true - else - @trailing_prec_seen = true - end - builder = val[0] - builder.precedence_sym = sym - result = builder + @prec_seen = true + node = Grammar::Node::RuleRhs::Prec.new( + token: val[2], + location: val[2].loc + ) + result.append(node) } - alias: string_as_id? { result = val[0].s_value if val[0] } + alias: string_as_id? symbol_declarations: TAG? symbol+ { - result = if val[0] - [{tag: val[0], tokens: val[1]}] - else - [{tag: nil, tokens: val[1]}] + result = val[1].map do |id| + Grammar::Node::Symbol.new( + id: id, tag: val[0], + location: id.loc + ) + end + } + | symbol_declarations TAG symbol+ + { + syms = val[2].map do |id| + Grammar::Node::Symbol.new( + id: id, tag: val[1], + location: id.loc + ) end + result = val[0].concat(syms) } - | symbol_declarations TAG symbol+ { result = val[0].append({tag: val[1], tokens: val[2]}) } symbol: id @@ -331,9 +396,43 @@ rule } token_declarations_for_precedence: - id+ { result = [{tag: nil, tokens: val[0]}] } - | (TAG id+)+ { result = val[0].map {|tag, ids| {tag: tag, tokens: ids} } } - | id+ TAG id+ { result = [{tag: nil, tokens: val[0]}, {tag: val[1], tokens: val[2]}] } + id+ + { + result = val[0].map do |id| + Grammar::Node::Token.new( + id: id, + location: id.loc + ) + end + } + | (TAG id+)+ + { + result = val[0].flat_map do |tag, ids| + ids.map do |id| + Grammar::Node::Token.new( + id: id, + tag: tag, + location: id.loc + ) + end + end + } + | id+ TAG id+ + { + # result = [{tag: nil, tokens: val[0]}, {tag: val[1], tokens: val[2]}] + result = val[0].map do |id| + Grammar::Node::Token.new( + id: id, + location: id.loc + ) + end + val[2].map do |id| + Grammar::Node::Token.new( + id: id, + tag: val[1], + location: id.loc + ) + end + } id: IDENTIFIER @@ -346,99 +445,94 @@ rule rules: IDENT_COLON named_ref? ":" rhs_list { - lhs = val[0] - lhs.alias_name = val[1] - val[3].each do |builder| - builder.lhs = lhs - builder.complete_input - @grammar.add_rule_builder(builder) - end + result = val[3].map do |rhs| + Grammar::Node::Rule.new( + id: val[0], + alias_name: val[1], + rhs: rhs, + location: val[0].loc + ) + end } rhs_list: rhs { - if val[0].rhs.count > 1 - empties = val[0].rhs.select { |sym| sym.is_a?(Lrama::Lexer::Token::Empty) } + if val[0].reject {|sym| sym.is_a?(Grammar::Node::RuleRhs::Action) || sym.is_a?(Grammar::Node::RuleRhs::Prec) }.count > 1 + empties = val[0].select { |sym| sym.is_a?(Grammar::Node::RuleRhs::Empty) } empties.each do |empty| on_action_error("%empty on non-empty rule", empty) end end - builder = val[0] - if !builder.line - builder.line = @lexer.line - 1 - end - result = [builder] + result = [val[0]] } | rhs_list "|" rhs { - builder = val[2] - if !builder.line - builder.line = @lexer.line - 1 - end - result = val[0].append(builder) + result = val[0].append(val[2]) } rhs: /* empty */ { reset_precs - result = @grammar.create_rule_builder(@rule_counter, @midrule_action_counter) + result = [] } | rhs "%empty" { - builder = val[0] - builder.add_rhs(Lrama::Lexer::Token::Empty.new(location: @lexer.location)) - result = builder + node = Grammar::Node::RuleRhs::Empty.new(location: val[1].loc) + result.append(node) } | rhs symbol named_ref? { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = val[1] - token.alias_name = val[2] - builder = val[0] - builder.add_rhs(token) - result = builder + node = Grammar::Node::RuleRhs::Symbol.new( + token: val[1], alias_name: val[2], + location: val[1].loc + ) + result.append(node) } | rhs symbol parameterized_suffix named_ref? TAG? { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = Lrama::Lexer::Token::InstantiateRule.new(s_value: val[2], alias_name: val[3], location: @lexer.location, args: [val[1]], lhs_tag: val[4]) - builder = val[0] - builder.add_rhs(token) - builder.line = val[1].first_line - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[2], args: [val[1]], + alias_name: val[3], lhs_tag: val[4], + location: merge_locations(val[1].loc, val[4]&.loc) + ) + result.append(node) } | rhs IDENTIFIER "(" parameterized_args ")" named_ref? TAG? { on_action_error("intermediate %prec in a rule", val[1]) if @trailing_prec_seen - token = Lrama::Lexer::Token::InstantiateRule.new(s_value: val[1].s_value, alias_name: val[5], location: @lexer.location, args: val[3], lhs_tag: val[6]) - builder = val[0] - builder.add_rhs(token) - builder.line = val[1].first_line - result = builder + node = Grammar::Node::RuleRhs::InstantiateRule.new( + s_value: val[1].s_value, args: val[3], + alias_name: val[5], lhs_tag: val[6], + location: merge_locations(val[1].loc, val[6]&.loc) + ) + result.append(node) } | rhs action named_ref? TAG? { - user_code = val[1] - user_code.alias_name = val[2] - user_code.tag = val[3] - builder = val[0] - builder.user_code = user_code - result = builder + node = Grammar::Node::RuleRhs::Action.new( + code: val[1], alias_name: val[2], tag: val[3], + location: val[1].loc + ) + result.append(node) } | rhs "%prec" symbol { on_action_error("multiple %prec in a rule", val[0]) if prec_seen? - sym = @grammar.find_symbol_by_id!(val[2]) - if val[0].rhs.empty? + if val[0].empty? @opening_prec_seen = true else @trailing_prec_seen = true end - builder = val[0] - builder.precedence_sym = sym - result = builder + + node = Grammar::Node::RuleRhs::Prec.new( + token: val[2], + location: val[2].loc + ) + result.append(node) } parameterized_suffix: @@ -487,8 +581,7 @@ rule C_DECLARATION { end_c_declaration - @grammar.epilogue_first_lineno = val[0].first_line + 1 - @grammar.epilogue = val[2].s_value + result = Grammar::Node::EpilogueDecl.new(code: val[2], location: merge_locations(val[0].loc, val[2].loc)) } variable: id @@ -519,10 +612,12 @@ def parse message = "parse '#{File.basename(@path)}'" report_duration(message) do @lexer = Lrama::Lexer.new(@grammar_file) - @grammar = Lrama::Grammar.new(@rule_counter, @locations, @define) + @grammar = Lrama::Grammar.new(@rule_counter, @midrule_action_counter, @locations, @define) @precedence_number = 0 reset_precs - do_parse + nodes = do_parse + @grammar.nodes = nodes + @grammar.evaluate_nodes @grammar end end @@ -553,7 +648,10 @@ def on_error(error_token_id, error_value, value_stack) end def on_action_error(error_message, error_value) - if error_value.is_a?(Lrama::Lexer::Token::Base) + case error_value + when Lrama::Lexer::Token::Base + location = error_value.location + when Lrama::Grammar::Node::Base location = error_value.location else location = @lexer.location @@ -587,3 +685,17 @@ end def raise_parse_error(error_message, location) raise ParseError, location.generate_error_message(error_message) end + +def merge_locations(*locations) + locations = locations.compact + first = locations.first + last = locations.last + + Lexer::Location.new( + grammar_file: @grammar_file, + first_line: first.first_line, + first_column: first.first_column, + last_line: last.last_line, + last_column: last.last_column + ) +end diff --git a/sig/generated/lrama/grammar.rbs b/sig/generated/lrama/grammar.rbs index a5f1e28a4..5852949a7 100644 --- a/sig/generated/lrama/grammar.rbs +++ b/sig/generated/lrama/grammar.rbs @@ -66,7 +66,7 @@ module Lrama @locations: bool - @define: Hash[String, String] + @define: Hash[String, String?] @required: bool @@ -76,6 +76,8 @@ module Lrama @start_nterm: Lrama::Lexer::Token::Base? + @nodes: Array[Node::Base] + extend Forwardable attr_reader percent_codes: Array[PercentCode] @@ -132,12 +134,17 @@ module Lrama attr_accessor locations: bool - attr_accessor define: Hash[String, String] + attr_accessor define: Hash[String, String?] attr_accessor required: bool - # @rbs (Counter rule_counter, bool locations, Hash[String, String] define) -> void - def initialize: (Counter rule_counter, bool locations, Hash[String, String] define) -> void + attr_accessor nodes: Array[Node::Base] + + # @rbs (Counter rule_counter, bool locations, Hash[String, String?] define) -> void + def initialize: (Counter rule_counter, bool locations, Hash[String, String?] define) -> void + + # @rbs () -> void + def evaluate_nodes: () -> void # @rbs (Counter rule_counter, Counter midrule_action_counter) -> RuleBuilder def create_rule_builder: (Counter rule_counter, Counter midrule_action_counter) -> RuleBuilder @@ -154,8 +161,8 @@ module Lrama # @rbs (ident_or_tags: Array[Lexer::Token::Ident|Lexer::Token::Tag], token_code: Lexer::Token::UserCode, lineno: Integer) -> Array[ErrorToken] def add_error_token: (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], token_code: Lexer::Token::UserCode, lineno: Integer) -> Array[ErrorToken] - # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> Array[Type] - def add_type: (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> Array[Type] + # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> Array[Type] + def add_type: (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> Array[Type] # @rbs (Grammar::Symbol sym, Integer precedence, String s_value, Integer lineno) -> Precedence def add_nonassoc: (Grammar::Symbol sym, Integer precedence, String s_value, Integer lineno) -> Precedence @@ -229,6 +236,9 @@ module Lrama private + # @rbs () -> void + def _evaluate_nodes: () -> void + # @rbs () -> void def sort_precedence: () -> void diff --git a/sig/generated/lrama/grammar/node.rbs b/sig/generated/lrama/grammar/node.rbs new file mode 100644 index 000000000..05051fa9b --- /dev/null +++ b/sig/generated/lrama/grammar/node.rbs @@ -0,0 +1,2 @@ +# Generated from lib/lrama/grammar/node.rb with RBS::Inline + diff --git a/sig/generated/lrama/grammar/node/after_pop_stack_decl.rbs b/sig/generated/lrama/grammar/node/after_pop_stack_decl.rbs new file mode 100644 index 000000000..6066abf6c --- /dev/null +++ b/sig/generated/lrama/grammar/node/after_pop_stack_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/after_pop_stack_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class AfterPopStackDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/after_reduce_decl.rbs b/sig/generated/lrama/grammar/node/after_reduce_decl.rbs new file mode 100644 index 000000000..a3239ac07 --- /dev/null +++ b/sig/generated/lrama/grammar/node/after_reduce_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/after_reduce_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class AfterReduceDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/after_shift_decl.rbs b/sig/generated/lrama/grammar/node/after_shift_decl.rbs new file mode 100644 index 000000000..666e4e797 --- /dev/null +++ b/sig/generated/lrama/grammar/node/after_shift_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/after_shift_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class AfterShiftDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/after_shift_error_token_decl.rbs b/sig/generated/lrama/grammar/node/after_shift_error_token_decl.rbs new file mode 100644 index 000000000..21bfc4963 --- /dev/null +++ b/sig/generated/lrama/grammar/node/after_shift_error_token_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/after_shift_error_token_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class AfterShiftErrorTokenDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/base.rbs b/sig/generated/lrama/grammar/node/base.rbs new file mode 100644 index 000000000..e65174553 --- /dev/null +++ b/sig/generated/lrama/grammar/node/base.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/base.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class Base + attr_reader location: Lexer::Location + + # @rbs (location: Lexer::Location) -> void + def initialize: (location: Lexer::Location) -> void + + alias loc location + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/before_reduce_decl.rbs b/sig/generated/lrama/grammar/node/before_reduce_decl.rbs new file mode 100644 index 000000000..91df2a308 --- /dev/null +++ b/sig/generated/lrama/grammar/node/before_reduce_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/before_reduce_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class BeforeReduceDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/code_decl.rbs b/sig/generated/lrama/grammar/node/code_decl.rbs new file mode 100644 index 000000000..5e1f8c542 --- /dev/null +++ b/sig/generated/lrama/grammar/node/code_decl.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/code_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class CodeDecl < Base + attr_reader id: Lexer::Token::Ident + + attr_reader code: Lexer::Token::UserCode + + # @rbs (id: Lexer::Token::Ident, code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/define_decl.rbs b/sig/generated/lrama/grammar/node/define_decl.rbs new file mode 100644 index 000000000..25f60349a --- /dev/null +++ b/sig/generated/lrama/grammar/node/define_decl.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/define_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class DefineDecl < Base + attr_reader variable: String + + attr_reader value: String? + + # @rbs (variable: String, value: String?, location: Lexer::Location) -> void + def initialize: (variable: String, value: String?, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/destructor_decl.rbs b/sig/generated/lrama/grammar/node/destructor_decl.rbs new file mode 100644 index 000000000..d0cd3884d --- /dev/null +++ b/sig/generated/lrama/grammar/node/destructor_decl.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/destructor_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class DestructorDecl < Base + attr_reader ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag] + + attr_reader code: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/epilogue_decl.rbs b/sig/generated/lrama/grammar/node/epilogue_decl.rbs new file mode 100644 index 000000000..4bf83905f --- /dev/null +++ b/sig/generated/lrama/grammar/node/epilogue_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/epilogue_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class EpilogueDecl < Base + attr_reader code: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/error_token_decl.rbs b/sig/generated/lrama/grammar/node/error_token_decl.rbs new file mode 100644 index 000000000..ccf23b42e --- /dev/null +++ b/sig/generated/lrama/grammar/node/error_token_decl.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/error_token_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class ErrorTokenDecl < Base + attr_reader ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag] + + attr_reader code: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/expect_decl.rbs b/sig/generated/lrama/grammar/node/expect_decl.rbs new file mode 100644 index 000000000..35bf81663 --- /dev/null +++ b/sig/generated/lrama/grammar/node/expect_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/expect_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class ExpectDecl < Base + attr_reader number: Integer + + # @rbs (number: Integer, location: Lexer::Location) -> void + def initialize: (number: Integer, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/initial_action_decl.rbs b/sig/generated/lrama/grammar/node/initial_action_decl.rbs new file mode 100644 index 000000000..a1bfc684e --- /dev/null +++ b/sig/generated/lrama/grammar/node/initial_action_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/initial_action_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class InitialActionDecl < Base + attr_reader code: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/lex_param_decl.rbs b/sig/generated/lrama/grammar/node/lex_param_decl.rbs new file mode 100644 index 000000000..c7daed222 --- /dev/null +++ b/sig/generated/lrama/grammar/node/lex_param_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/lex_param_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class LexParamDecl < Base + attr_reader params: Array[Lexer::Token::UserCode] + + # @rbs (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + def initialize: (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/locations_decl.rbs b/sig/generated/lrama/grammar/node/locations_decl.rbs new file mode 100644 index 000000000..0d1df32b2 --- /dev/null +++ b/sig/generated/lrama/grammar/node/locations_decl.rbs @@ -0,0 +1,10 @@ +# Generated from lib/lrama/grammar/node/locations_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class LocationsDecl < Base + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/no_stdlib_decl.rbs b/sig/generated/lrama/grammar/node/no_stdlib_decl.rbs new file mode 100644 index 000000000..08c325910 --- /dev/null +++ b/sig/generated/lrama/grammar/node/no_stdlib_decl.rbs @@ -0,0 +1,10 @@ +# Generated from lib/lrama/grammar/node/no_stdlib_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class NoStdlibDecl < Base + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/nterm_decl.rbs b/sig/generated/lrama/grammar/node/nterm_decl.rbs new file mode 100644 index 000000000..366b6ead3 --- /dev/null +++ b/sig/generated/lrama/grammar/node/nterm_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/nterm_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class NtermDecl < Base + attr_reader symbols: Array[Node::Symbol] + + # @rbs (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + def initialize: (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/parameterized_rule.rbs b/sig/generated/lrama/grammar/node/parameterized_rule.rbs new file mode 100644 index 000000000..c82cd6a3f --- /dev/null +++ b/sig/generated/lrama/grammar/node/parameterized_rule.rbs @@ -0,0 +1,22 @@ +# Generated from lib/lrama/grammar/node/parameterized_rule.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class ParameterizedRule < Base + attr_reader name: String + + attr_reader parameters: Array[Lexer::Token::Base] + + attr_reader tag: Lexer::Token::Tag? + + attr_reader rhs_list: Array[Array[Node::Base]] + + attr_reader is_inline: bool + + # @rbs (name: String, parameters: Array[Lexer::Token::Base], ?tag: Lexer::Token::Tag?, rhs_list: Array[Array[Node::Base]], is_inline: bool, location: Lexer::Location) -> void + def initialize: (name: String, parameters: Array[Lexer::Token::Base], rhs_list: Array[Array[Node::Base]], is_inline: bool, location: Lexer::Location, ?tag: Lexer::Token::Tag?) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/parse_param_decl.rbs b/sig/generated/lrama/grammar/node/parse_param_decl.rbs new file mode 100644 index 000000000..3559655fd --- /dev/null +++ b/sig/generated/lrama/grammar/node/parse_param_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/parse_param_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class ParseParamDecl < Base + attr_reader params: Array[Lexer::Token::UserCode] + + # @rbs (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + def initialize: (params: Array[Lexer::Token::UserCode], location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/precedence_decl.rbs b/sig/generated/lrama/grammar/node/precedence_decl.rbs new file mode 100644 index 000000000..2272e7080 --- /dev/null +++ b/sig/generated/lrama/grammar/node/precedence_decl.rbs @@ -0,0 +1,20 @@ +# Generated from lib/lrama/grammar/node/precedence_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class PrecedenceDecl < Base + type type_enum = :left | :right | :precedence | :nonassoc + + attr_reader type: type_enum + + attr_reader tokens: Array[Node::Token] + + attr_reader number: Integer + + # @rbs (type: type_enum, tokens: Array[Node::Token], number: Integer, location: Lexer::Location) -> void + def initialize: (type: type_enum, tokens: Array[Node::Token], number: Integer, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/printer_decl.rbs b/sig/generated/lrama/grammar/node/printer_decl.rbs new file mode 100644 index 000000000..0f5ac0185 --- /dev/null +++ b/sig/generated/lrama/grammar/node/printer_decl.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/printer_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class PrinterDecl < Base + attr_reader ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag] + + attr_reader code: Lexer::Token::UserCode + + # @rbs (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (ident_or_tags: Array[Lexer::Token::Ident | Lexer::Token::Tag], code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/prologue_decl.rbs b/sig/generated/lrama/grammar/node/prologue_decl.rbs new file mode 100644 index 000000000..07cbf2d86 --- /dev/null +++ b/sig/generated/lrama/grammar/node/prologue_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/prologue_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class PrologueDecl < Base + attr_reader code: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/require_decl.rbs b/sig/generated/lrama/grammar/node/require_decl.rbs new file mode 100644 index 000000000..193b8f6e0 --- /dev/null +++ b/sig/generated/lrama/grammar/node/require_decl.rbs @@ -0,0 +1,10 @@ +# Generated from lib/lrama/grammar/node/require_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class RequireDecl < Base + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule.rbs b/sig/generated/lrama/grammar/node/rule.rbs new file mode 100644 index 000000000..fe897b095 --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule.rbs @@ -0,0 +1,18 @@ +# Generated from lib/lrama/grammar/node/rule.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class Rule < Base + attr_reader id: Lexer::Token::Base + + attr_reader alias_name: String? + + attr_reader rhs: Array[Node::Base] + + # @rbs (id: Lexer::Token::Base, ?alias_name: String?, rhs: Array[Node::Base], location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Base, rhs: Array[Node::Base], location: Lexer::Location, ?alias_name: String?) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs.rbs b/sig/generated/lrama/grammar/node/rule_rhs.rbs new file mode 100644 index 000000000..3208b1a3c --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs.rbs @@ -0,0 +1,10 @@ +# Generated from lib/lrama/grammar/node/rule_rhs.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs/action.rbs b/sig/generated/lrama/grammar/node/rule_rhs/action.rbs new file mode 100644 index 000000000..b0ce8dbd9 --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs/action.rbs @@ -0,0 +1,20 @@ +# Generated from lib/lrama/grammar/node/rule_rhs/action.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + class Action < Node::Base + attr_reader code: Lexer::Token::UserCode + + attr_reader alias_name: String? + + attr_reader tag: Lexer::Token::Tag? + + # @rbs (code: Lexer::Token::UserCode, ?alias_name: String?, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize: (code: Lexer::Token::UserCode, location: Lexer::Location, ?alias_name: String?, ?tag: Lexer::Token::Tag?) -> void + end + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs/empty.rbs b/sig/generated/lrama/grammar/node/rule_rhs/empty.rbs new file mode 100644 index 000000000..942bb8aa9 --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs/empty.rbs @@ -0,0 +1,12 @@ +# Generated from lib/lrama/grammar/node/rule_rhs/empty.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + class Empty < Node::Base + end + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs/instantiate_rule.rbs b/sig/generated/lrama/grammar/node/rule_rhs/instantiate_rule.rbs new file mode 100644 index 000000000..ecb46d51d --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs/instantiate_rule.rbs @@ -0,0 +1,22 @@ +# Generated from lib/lrama/grammar/node/rule_rhs/instantiate_rule.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + class InstantiateRule < Node::Base + attr_reader s_value: String + + attr_reader args: Array[Lexer::Token::Base] + + attr_reader alias_name: String? + + attr_reader lhs_tag: Lexer::Token::Tag? + + # @rbs (s_value: String, args: Array[Lexer::Token::Base], ?alias_name: String?, ?lhs_tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize: (s_value: String, args: Array[Lexer::Token::Base], location: Lexer::Location, ?alias_name: String?, ?lhs_tag: Lexer::Token::Tag?) -> void + end + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs/prec.rbs b/sig/generated/lrama/grammar/node/rule_rhs/prec.rbs new file mode 100644 index 000000000..ee6e8426e --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs/prec.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/rule_rhs/prec.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + class Prec < Node::Base + attr_reader token: Lexer::Token::Base + + # @rbs (token: Lexer::Token::Base, location: Lexer::Location) -> void + def initialize: (token: Lexer::Token::Base, location: Lexer::Location) -> void + end + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/rule_rhs/symbol.rbs b/sig/generated/lrama/grammar/node/rule_rhs/symbol.rbs new file mode 100644 index 000000000..d2a55dea8 --- /dev/null +++ b/sig/generated/lrama/grammar/node/rule_rhs/symbol.rbs @@ -0,0 +1,21 @@ +# Generated from lib/lrama/grammar/node/rule_rhs/symbol.rb with RBS::Inline + +module Lrama + class Grammar + module Node + module RuleRhs + class Symbol < Node::Base + attr_reader token: Lexer::Token::Base + + attr_reader alias_name: String? + + # @rbs (token: Lexer::Token::Base, ?alias_name: String?, location: Lexer::Location) -> void + def initialize: (token: Lexer::Token::Base, location: Lexer::Location, ?alias_name: String?) -> void + + # @rbs () -> String + def s_value: () -> String + end + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/start_decl.rbs b/sig/generated/lrama/grammar/node/start_decl.rbs new file mode 100644 index 000000000..221cd03e4 --- /dev/null +++ b/sig/generated/lrama/grammar/node/start_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/start_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class StartDecl < Base + attr_reader id: Lexer::Token::Ident + + # @rbs (id: Lexer::Token::Ident, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Ident, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/symbol.rbs b/sig/generated/lrama/grammar/node/symbol.rbs new file mode 100644 index 000000000..45e41db7e --- /dev/null +++ b/sig/generated/lrama/grammar/node/symbol.rbs @@ -0,0 +1,16 @@ +# Generated from lib/lrama/grammar/node/symbol.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class Symbol < Base + attr_reader id: Lexer::Token::Base + + attr_accessor tag: Lexer::Token::Tag? + + # @rbs (id: Lexer::Token::Base, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Base, location: Lexer::Location, ?tag: Lexer::Token::Tag?) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/token.rbs b/sig/generated/lrama/grammar/node/token.rbs new file mode 100644 index 000000000..042eea08a --- /dev/null +++ b/sig/generated/lrama/grammar/node/token.rbs @@ -0,0 +1,20 @@ +# Generated from lib/lrama/grammar/node/token.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class Token < Base + attr_reader id: Lexer::Token::Base + + attr_reader token_id: Integer? + + attr_reader alias_name: String? + + attr_accessor tag: Lexer::Token::Tag? + + # @rbs (id: Lexer::Token::Base, ?token_id: Integer?, ?alias_name: String?, ?tag: Lexer::Token::Tag?, location: Lexer::Location) -> void + def initialize: (id: Lexer::Token::Base, location: Lexer::Location, ?token_id: Integer?, ?alias_name: String?, ?tag: Lexer::Token::Tag?) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/token_decl.rbs b/sig/generated/lrama/grammar/node/token_decl.rbs new file mode 100644 index 000000000..1f1004e61 --- /dev/null +++ b/sig/generated/lrama/grammar/node/token_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/token_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class TokenDecl < Base + attr_reader tokens: Array[Node::Token] + + # @rbs (tokens: Array[Node::Token], location: Lexer::Location) -> void + def initialize: (tokens: Array[Node::Token], location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/type_decl.rbs b/sig/generated/lrama/grammar/node/type_decl.rbs new file mode 100644 index 000000000..dc8df9173 --- /dev/null +++ b/sig/generated/lrama/grammar/node/type_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/type_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class TypeDecl < Base + attr_reader symbols: Array[Node::Symbol] + + # @rbs (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + def initialize: (symbols: Array[Node::Symbol], location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/node/union_decl.rbs b/sig/generated/lrama/grammar/node/union_decl.rbs new file mode 100644 index 000000000..88100cea6 --- /dev/null +++ b/sig/generated/lrama/grammar/node/union_decl.rbs @@ -0,0 +1,14 @@ +# Generated from lib/lrama/grammar/node/union_decl.rb with RBS::Inline + +module Lrama + class Grammar + module Node + class UnionDecl < Base + attr_reader code: Lexer::Token::UserCode + + # @rbs (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + def initialize: (code: Lexer::Token::UserCode, location: Lexer::Location) -> void + end + end + end +end diff --git a/sig/generated/lrama/grammar/symbols/resolver.rbs b/sig/generated/lrama/grammar/symbols/resolver.rbs index 2e5f2ebf7..9c6bf527e 100644 --- a/sig/generated/lrama/grammar/symbols/resolver.rbs +++ b/sig/generated/lrama/grammar/symbols/resolver.rbs @@ -21,6 +21,8 @@ module Lrama def token_to_symbol: (Lexer::Token::Base token) -> Grammar::Symbol + def find_term_by_s_value: (::String s_value) -> Grammar::Symbol? + def find_symbol_by_s_value!: (::String s_value) -> Grammar::Symbol def fill_nterm_type: (Array[Grammar::Type] types) -> void diff --git a/sig/generated/lrama/grammar/type.rbs b/sig/generated/lrama/grammar/type.rbs index 563e1095f..187f45037 100644 --- a/sig/generated/lrama/grammar/type.rbs +++ b/sig/generated/lrama/grammar/type.rbs @@ -5,14 +5,14 @@ module Lrama class Type @id: Lexer::Token::Base - @tag: Lexer::Token::Tag + @tag: Lexer::Token::Tag? attr_reader id: Lexer::Token::Base - attr_reader tag: Lexer::Token::Tag + attr_reader tag: Lexer::Token::Tag? - # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> void - def initialize: (id: Lexer::Token::Base, tag: Lexer::Token::Tag) -> void + # @rbs (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> void + def initialize: (id: Lexer::Token::Base, tag: Lexer::Token::Tag?) -> void # @rbs (Grammar::Type other) -> bool def ==: (Grammar::Type other) -> bool diff --git a/sig/generated/lrama/lexer/token/base.rbs b/sig/generated/lrama/lexer/token/base.rbs index 3879d815e..ab11fbb7d 100644 --- a/sig/generated/lrama/lexer/token/base.rbs +++ b/sig/generated/lrama/lexer/token/base.rbs @@ -8,14 +8,16 @@ module Lrama attr_reader location: Location - attr_accessor alias_name: String + attr_accessor alias_name: String? attr_accessor referred: bool attr_reader errors: Array[String] - # @rbs (s_value: String, ?alias_name: String, ?location: Location) -> void - def initialize: (s_value: String, ?alias_name: String, ?location: Location) -> void + # @rbs (s_value: String, ?alias_name: String?, ?location: Location) -> void + def initialize: (s_value: String, ?alias_name: String?, ?location: Location) -> void + + alias loc location # @rbs () -> String def to_s: () -> String diff --git a/sig/generated/lrama/lexer/token/instantiate_rule.rbs b/sig/generated/lrama/lexer/token/instantiate_rule.rbs index 9448d05fa..3ef5e6bb5 100644 --- a/sig/generated/lrama/lexer/token/instantiate_rule.rbs +++ b/sig/generated/lrama/lexer/token/instantiate_rule.rbs @@ -8,8 +8,8 @@ module Lrama attr_reader lhs_tag: Lexer::Token::Tag? - # @rbs (s_value: String, ?alias_name: String, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void - def initialize: (s_value: String, ?alias_name: String, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void + # @rbs (s_value: String, ?alias_name: String?, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void + def initialize: (s_value: String, ?alias_name: String?, ?location: Location, ?args: Array[Lexer::Token::Base], ?lhs_tag: Lexer::Token::Tag?) -> void # @rbs () -> String def rule_name: () -> String diff --git a/sig/generated/lrama/lexer/token/user_code.rbs b/sig/generated/lrama/lexer/token/user_code.rbs index a2ce8af81..7cbcb5149 100644 --- a/sig/generated/lrama/lexer/token/user_code.rbs +++ b/sig/generated/lrama/lexer/token/user_code.rbs @@ -4,7 +4,7 @@ module Lrama class Lexer module Token class UserCode < Base - attr_accessor tag: Lexer::Token::Tag + attr_accessor tag: Lexer::Token::Tag? # @rbs () -> Array[Lrama::Grammar::Reference] def references: () -> Array[Lrama::Grammar::Reference]