class AdLint::Cpp::MacroTable

Public Class Methods

new() click to toggle source
# File lib/adlint/cpp/macro.rb, line 703
def initialize
  @macros = {}
  predefine_special_macros
end

Public Instance Methods

define(macro) click to toggle source
# File lib/adlint/cpp/macro.rb, line 715
def define(macro)
  @macros[macro.name.value] = macro
  self
end
lookup(name_str) click to toggle source
# File lib/adlint/cpp/macro.rb, line 725
def lookup(name_str)
  @macros[name_str]
end
notify_function_like_macro_replacement(macro, replacing_toks, args, rslt_toks) click to toggle source
# File lib/adlint/cpp/macro.rb, line 759
def notify_function_like_macro_replacement(macro, replacing_toks, args,
                                           rslt_toks)
  on_function_like_macro_replacement.invoke(macro, replacing_toks, args,
                                            rslt_toks)
end
notify_last_backslash_ignored(tok) click to toggle source
# File lib/adlint/cpp/macro.rb, line 769
def notify_last_backslash_ignored(tok)
  on_last_backslash_ignored.invoke(tok)
end
notify_object_like_macro_replacement(macro, replacing_toks, rslt_toks) click to toggle source
# File lib/adlint/cpp/macro.rb, line 755
def notify_object_like_macro_replacement(macro, replacing_toks, rslt_toks)
  on_object_like_macro_replacement.invoke(macro, replacing_toks, rslt_toks)
end
notify_sharpsharp_operator_evaled(lhs_tok, rhs_tok, new_toks) click to toggle source
# File lib/adlint/cpp/macro.rb, line 765
def notify_sharpsharp_operator_evaled(lhs_tok, rhs_tok, new_toks)
  on_sharpsharp_operator_evaled.invoke(lhs_tok, rhs_tok, new_toks)
end
replace(toks, repl_ctxt = nil) click to toggle source
# File lib/adlint/cpp/macro.rb, line 729
def replace(toks, repl_ctxt = nil)
  replaced = false
  idx = 0

  while tok = toks[idx]
    case tok.value
    when "defined"
      in_defined = true
    when "(", ")"
      ;
    else
      if in_defined
        in_defined = false
      else
        if new_idx = do_replace(toks, idx, repl_ctxt)
          idx = new_idx
          replaced = true
        end
      end
    end
    idx += 1
  end

  replaced
end
undef(name_str) click to toggle source
# File lib/adlint/cpp/macro.rb, line 720
def undef(name_str)
  @macros.delete(name_str)
  self
end

Private Instance Methods

do_replace(toks, idx, repl_ctxt) click to toggle source
# File lib/adlint/cpp/macro.rb, line 774
def do_replace(toks, idx, repl_ctxt)
  repl_ctxt ||= MacroReplacementContext.new

  return nil unless tok = toks[idx] and macro = lookup(tok.value)
  return nil if repl_ctxt.hidden?(tok, macro.name.value)

  size = macro.replaceable_size(toks.drop(idx))

  if toks[idx, size].all? { |t| t.need_no_further_replacement? }
    return nil
  end

  expanded = macro.expand(toks[idx, size], self, repl_ctxt)
  repl_ctxt.add_to_hide_set(toks[idx], expanded, macro.name.value)

  # NOTE: The ISO C99 standard says;
  #
  # 6.10.3.4 Rescanning and further replacement
  #
  # 1 After all parameters in the replacement list have been substituted
  #   and # and ## processing has take place, all placemarker preprocessing
  #   tokens are removed.  Then, the resulting preprocessing token sequence
  #   is rescanned, along with all subsequent preprocessing tokens of the
  #   source file, for more macro names to replace.
  #
  # 2 If the name of the macro being replaced is found during this scan of
  #   the replacement list (not including the rest of the source file's
  #   preprocessing tokens), it is not replaced.  Furthermore, if any
  #   nested replacements encounter the name of the macro being replaced,
  #   it is not replaced.  These nonreplaced macro name preprocessing
  #   tokens are no longer available for further replacement even if they
  #   are later (re)examined in contexts in which that macro name
  #   preprocessing token whould otherwise have been replaced.
  while replace(expanded, repl_ctxt); end
  toks[idx, size] = expanded

  idx + expanded.size - 1
end
predefine_special_macros() click to toggle source
# File lib/adlint/cpp/macro.rb, line 813
def predefine_special_macros
  define(DateMacro.new)
  define(FileMacro.new)
  define(LineMacro.new)
  define(StdcMacro.new)
  define(StdcHostedMacro.new)
  define(StdcMbMightNeqWcMacro.new)
  define(StdcVersionMacro.new)
  define(TimeMacro.new)
  define(StdcIec559Macro.new)
  define(StdcIec559ComplexMacro.new)
  define(StdcIso10646Macro.new)
  define(PragmaOperator.new)
  define(LintSpecificMacro1.new)
  define(LintSpecificMacro2.new)
  define(LintSpecificMacro3.new)
  define(LintSpecificMacro4.new)
  define(AdLintSpecificMacro1.new)
  define(AdLintSpecificMacro2.new)
  define(AdLintSpecificMacro3.new)
  define(AdLintSpecificMacro4.new)
end