123456789_123456789_123456789_123456789_123456789_

Class: RDoc::Markdown::Literals

Relationships & Source Files
Namespace Children
Classes:
Exceptions:
Inherits: Object
Defined in: lib/rdoc/markdown/literals.rb

Overview

This set of literals is for Ruby 1.9 regular expressions and gives full unicode support.

Unlike peg-markdown, this set of literals recognizes Unicode alphanumeric characters, newlines and spaces.

Constant Summary

Class Method Summary

Instance Attribute Summary

Instance Method Summary

Constructor Details

.new(str, debug = false) ⇒ Literals

This method is for internal use only.

This is distinct from setup_parser so that a standalone parser can redefine RDoc::Markdown#initialize and still have access to the proper parser setup code.

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 17

def initialize(str, debug=false)
  setup_parser(str, debug)
end

Class Method Details

.rule_info(name, rendered)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 395

def self.rule_info(name, rendered)
  RuleInfo.new(name, rendered)
end

Instance Attribute Details

#failed_rule (readonly)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 200

attr_reader :failed_rule

#failing_rule_offset (readonly)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 37

attr_reader :failing_rule_offset

#pos (rw)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 38

attr_accessor :result, :pos

#result (rw)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 38

attr_accessor :result, :pos

#string (readonly)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 36

attr_reader :string

Instance Method Details

#_Alphanumeric

Alphanumeric = /pWord/

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 405

def _Alphanumeric
  _tmp = scan(/\G(?-mix:\p{Word})/)
  set_failed_rule :_Alphanumeric unless _tmp
  return _tmp
end

#_AlphanumericAscii

AlphanumericAscii = /[A-Za-z0-9]/

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 412

def _AlphanumericAscii
  _tmp = scan(/\G(?-mix:[A-Za-z0-9])/)
  set_failed_rule :_AlphanumericAscii unless _tmp
  return _tmp
end

#_BOM

BOM = “uFEFF”

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 419

def _BOM
  _tmp = match_string("uFEFF")
  set_failed_rule :_BOM unless _tmp
  return _tmp
end

#_Newline

Newline = /n|rn?|pZl|pZp/

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 426

def _Newline
  _tmp = scan(/\G(?-mix:\n|\r\n?|\p{Zl}|\p{Zp})/)
  set_failed_rule :_Newline unless _tmp
  return _tmp
end

#_NonAlphanumeric

NonAlphanumeric = /p^Word/

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 433

def _NonAlphanumeric
  _tmp = scan(/\G(?-mix:\p{^Word})/)
  set_failed_rule :_NonAlphanumeric unless _tmp
  return _tmp
end

#_Spacechar

Spacechar = /t|pZs/

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 440

def _Spacechar
  _tmp = scan(/\G(?-mix:\t|\p{Zs})/)
  set_failed_rule :_Spacechar unless _tmp
  return _tmp
end

#apply(rule)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 331

def apply(rule)
  @result = nil
  if m = @memoizations[rule][@pos]
    @pos = m.pos
    if !m.set
      m.left_rec = true
      return nil
    end

    @result = m.result

    return m.ans
  else
    m = MemoEntry.new(nil, @pos)
    @memoizations[rule][@pos] = m
    start_pos = @pos

    ans = __send__ rule

    lr = m.left_rec

    m.move! ans, @pos, @result

    # Don't bother trying to grow the left recursion
    # if it's failing straight away (thus there is no seed)
    if ans and lr
      return grow_lr(rule, nil, start_pos, m)
    else
      return ans
    end
  end
end

#apply_with_args(rule, *args)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 297

def apply_with_args(rule, *args)
  @result = nil
  memo_key = [rule, args]
  if m = @memoizations[memo_key][@pos]
    @pos = m.pos
    if !m.set
      m.left_rec = true
      return nil
    end

    @result = m.result

    return m.ans
  else
    m = MemoEntry.new(nil, @pos)
    @memoizations[memo_key][@pos] = m
    start_pos = @pos

    ans = __send__ rule, *args

    lr = m.left_rec

    m.move! ans, @pos, @result

    # Don't bother trying to grow the left recursion
    # if it's failing straight away (thus there is no seed)
    if ans and lr
      return grow_lr(rule, args, start_pos, m)
    else
      return ans
    end
  end
end

#current_character(target = pos)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 79

def current_character(target=pos)
  if target < 0 || target >= string.size
    raise "Target position #{target} is outside of string"
  end
  string[target, 1]
end

#current_column(target = pos)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 40

def current_column(target=pos)
  if string[target] == "\n" && (c = string.rindex("\n", target-1) || -1)
    return target - c
  elsif c = string.rindex("\n", target)
    return target - c
  end

  target + 1
end

#current_line(target = pos)

This method is for internal use only.

See additional method definition at line 63.

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 70

def current_line(target=pos)
  if line = position_line_offsets.bsearch_index {|x| x > target }
    return line + 1
  end
  raise "Target position #{target} is outside of string"
end

#current_pos_info(target = pos)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 88

def current_pos_info(target=pos)
  l = current_line target
  c = current_column target
  ln = get_line(l-1)
  chr = string[target,1]
  KpegPosInfo.new(target, l, c, ln, chr)
end

#external_invoke(other, rule, *args)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 278

def external_invoke(other, rule, *args)
  old_pos = @pos
  old_string = @string

  set_string other.string, other.pos

  begin
    if val = __send__(rule, *args)
      other.pos = @pos
      other.result = @result
    else
      other.set_failed_rule "#{self.class}##{rule}"
    end
    val
  ensure
    set_string old_string, old_pos
  end
end

#failure_caret

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 147

def failure_caret
  p = current_pos_info @failing_rule_offset
  "#{p.line.chomp}\n#{' ' * (p.col - 1)}^"
end

#failure_character

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 152

def failure_character
  current_character @failing_rule_offset
end

#failure_info

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 135

def failure_info
  l = current_line @failing_rule_offset
  c = current_column @failing_rule_offset

  if @failed_rule.kind_of? Symbol
    info = self.class::Rules[@failed_rule]
    "line #{l}, column #{c}: failed rule '#{info.name}' = '#{info.rendered}'"
  else
    "line #{l}, column #{c}: failed rule '#{@failed_rule}'"
  end
end

#failure_oneline

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 156

def failure_oneline
  p = current_pos_info @failing_rule_offset

  if @failed_rule.kind_of? Symbol
    info = self.class::Rules[@failed_rule]
    "@#{p.lno}:#{p.col} failed rule '#{info.name}', got '#{p.char}'"
  else
    "@#{p.lno}:#{p.col} failed rule '#{@failed_rule}', got '#{p.char}'"
  end
end

#get_byte

This method is for internal use only.

See additional method definition at line 222.

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 232

def get_byte
  if @pos >= @string_size
    return nil
  end

  s = @string[@pos].ord
  @pos += 1
  s
end

#get_line(no)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 100

def get_line(no)
  loff = position_line_offsets
  if no < 0
    raise "Line No is out of range: #{no} < 0"
  elsif no >= loff.size
    raise "Line No is out of range: #{no} >= #{loff.size}"
  end
  lend = loff[no]-1
  lstart = no > 0 ? loff[no-1] : 0
  string[lstart..lend]
end

#get_text(start)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 114

def get_text(start)
  @string[start..@pos-1]
end

#grow_lr(rule, args, start_pos, m)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 364

def grow_lr(rule, args, start_pos, m)
  while true
    @pos = start_pos
    @result = m.result

    if args
      ans = __send__ rule, *args
    else
      ans = __send__ rule
    end
    return nil unless ans

    break if @pos <= m.pos

    m.move! ans, @pos, @result
  end

  @result = m.result
  @pos = m.pos
  return m.ans
end

#lines

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 96

def lines
  string.lines
end

#match_string(str)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 202

def match_string(str)
  len = str.size
  if @string[pos,len] == str
    @pos += len
    return str
  end

  return nil
end

#parse(rule = nil)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 243

def parse(rule=nil)
  # We invoke the rules indirectly via apply
  # instead of by just calling them as methods because
  # if the rules use left recursion, apply needs to
  # manage that.

  if !rule
    apply(:_root)
  else
    method = rule.gsub("-","_hyphen_")
    apply :"_#{method}"
  end
end

#position_line_offsets

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 50

def position_line_offsets
  unless @position_line_offsets
    @position_line_offsets = []
    total = 0
    string.each_line do |line|
      total += line.size
      @position_line_offsets << total
    end
  end
  @position_line_offsets
end

#raise_error

This method is for internal use only.

Raises:

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 170

def raise_error
  raise ParseError, failure_oneline
end

#scan(reg)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 212

def scan(reg)
  if m = reg.match(@string, @pos)
    @pos = m.end(0)
    return true
  end

  return nil
end

#set_failed_rule(name)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 193

def set_failed_rule(name)
  if @pos > @failing_rule_offset
    @failed_rule = name
    @failing_rule_offset = @pos
  end
end

#set_string(string, pos)

This method is for internal use only.

Sets the string and current parsing position for the parser.

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 119

def set_string string, pos
  @string = string
  @string_size = string ? string.size : 0
  @pos = pos
  @position_line_offsets = nil
end

#setup_foreign_grammar

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 402

def setup_foreign_grammar; end

#setup_parser(str, debug = false)

This method is for internal use only.

Prepares for parsing str. If you define a custom initialize you must call this method before #parse

[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 25

def setup_parser(str, debug=false)
  set_string str, 0
  @memoizations = Hash.new { |h,k| h[k] = {} }
  @result = nil
  @failed_rule = nil
  @failing_rule_offset = -1
  @line_offsets = nil

  setup_foreign_grammar
end

#show_error(io = STDOUT)

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 174

def show_error(io=STDOUT)
  error_pos = @failing_rule_offset
  p = current_pos_info(error_pos)

  io.puts "On line #{p.lno}, column #{p.col}:"

  if @failed_rule.kind_of? Symbol
    info = self.class::Rules[@failed_rule]
    io.puts "Failed to match '#{info.rendered}' (rule '#{info.name}')"
  else
    io.puts "Failed to match rule '#{@failed_rule}'"
  end

  io.puts "Got: #{p.char.inspect}"
  io.puts "=> #{p.line}"
  io.print(" " * (p.col + 2))
  io.puts "^"
end

#show_pos

This method is for internal use only.
[ GitHub ]

  
# File 'lib/rdoc/markdown/literals.rb', line 126

def show_pos
  width = 10
  if @pos < width
    "#{@pos} (\"#{@string[0,@pos]}\" @ \"#{@string[@pos,width]}\")"
  else
    "#{@pos} (\"... #{@string[@pos - width, width]}\" @ \"#{@string[@pos,width]}\")"
  end
end