From 92c7c60fedeab256ebf9fc15db5609d92ec393e6 Mon Sep 17 00:00:00 2001 From: Phillip Davis Date: Thu, 5 Mar 2026 12:59:32 -0500 Subject: [PATCH] fix(native): validate range content at parse time The native parser'ss terminal method accepted any content between [ and ] without validation. This meant invalid ranges like [-abc] were silently accepted instead of raising SyntaxError, despite the RANGE regex in terminals.rb correctly rejecting them. --- lib/ebnf/native.rb | 9 +++++++-- spec/native_spec.rb | 1 + 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/lib/ebnf/native.rb b/lib/ebnf/native.rb index f0b97e2..0503351 100644 --- a/lib/ebnf/native.rb +++ b/lib/ebnf/native.rb @@ -291,8 +291,13 @@ def terminal(s) l, s = s[1..-1].split(m.rstrip, 2) [Unescape.unescape(l).tap {|str| str.quote_style = (m == "'" ? :squote : :dquote)}, s] when '[' # RANGE, O_RANGE - # Includes RANGE and O_RANGE which can't include a ']' - l, s = s[1..-1].split(']', 2) + matched = s.match(Terminals::RANGE) || s.match(Terminals::O_RANGE) + unless matched + error("terminal", "illegal range: #{s.inspect}") + raise SyntaxError, "illegal range: #{s.inspect}" + end + l = matched[0][1..-2] + s = s[matched[0].length..] [[:range, Unescape.unescape(l)], s] when '#' # HEX s.match(/(#x\h+)(.*)$/) diff --git a/spec/native_spec.rb b/spec/native_spec.rb index eb9750a..a262dbe 100644 --- a/spec/native_spec.rb +++ b/spec/native_spec.rb @@ -128,6 +128,7 @@ { "diff missing second operand": %{rule ::= a -}, "unrecognized terminal" => %{rule ::= %foo%}, + "leading '-' in range" => %{rule ::= [-abc]}, }.each do |title, input| it title do expect {parse(input)}.to raise_error(SyntaxError)