lib/review/lineinput.rb in review-5.0.0 vs lib/review/lineinput.rb in review-5.1.0
- old
+ new
@@ -1,17 +1,127 @@
-require 'lineinput'
+#
+# Copyright (c) 2002-2020 Minero Aoki, Masayoshi Takahashi, Kenshi Muto
+#
+# This program is free software.
+# You can distribute/modify this program under the terms of
+# the GNU LGPL, Lesser General Public License version 2.1.
+#
+require 'review/exception'
module ReVIEW
- class LineInput < LineInput
+ class LineInput
+ INVALID_CHARACTER_PATTERN = /[\x00-\x08\x0b-\x0c\x0e-\x1f]/ # accept 0x09: TAB, 0x0a: LF, 0x0d: CR
+
+ attr_reader :lineno
+
+ def initialize(f)
+ @input = f
+ @buf = []
+ @lineno = 0
+ @eof_p = false
+ end
+
+ def inspect
+ "\#<#{self.class} file=#{@input.inspect} line=#{lineno}>"
+ end
+
+ def eof?
+ @eof_p
+ end
+
def skip_comment_lines
n = 0
while line = gets
unless line.strip =~ /\A\#@/
ungets(line)
return n
end
n += 1
end
n
+ end
+
+ def gets
+ unless @buf.empty?
+ @lineno += 1
+ return @buf.pop
+ end
+ return nil if @eof_p # to avoid ARGF blocking.
+
+ line = @input.gets
+ @eof_p = true unless line
+ @lineno += 1
+ invalid_char = lookup_invalid_char(line)
+ if invalid_char
+ raise SyntaxError, "found invalid control-sequence character (#{sprintf('%#x', invalid_char.codepoints[0])})."
+ end
+
+ line
+ end
+
+ def peek
+ line = gets
+ ungets(line) if line
+ line
+ end
+
+ def next?
+ peek ? true : false
+ end
+
+ def skip_blank_lines
+ n = 0
+ while line = gets
+ unless line.strip.empty?
+ ungets(line)
+ return n
+ end
+ n += 1
+ end
+ n
+ end
+
+ def each
+ while line = gets
+ yield line
+ end
+ end
+
+ def while_match(re)
+ while line = gets
+ unless re =~ line
+ ungets(line)
+ return
+ end
+ yield line
+ end
+ nil
+ end
+
+ def until_match(re)
+ while line = gets
+ if re =~ line
+ ungets(line)
+ return
+ end
+ yield line
+ end
+ nil
+ end
+
+ private
+
+ def ungets(line)
+ return unless line
+
+ @lineno -= 1
+ @buf.push(line)
+ line
+ end
+
+ def lookup_invalid_char(line)
+ if line =~ INVALID_CHARACTER_PATTERN
+ $&
+ end
end
end
end