lib/archruby/ruby/parser.rb in archruby-0.1.1 vs lib/archruby/ruby/parser.rb in archruby-0.2.0

- old
+ new

@@ -3,11 +3,12 @@ module Archruby module Ruby class Parser < SexpInterpreter - attr_reader :dependencies, :classes, :classes_and_dependencies + attr_reader :dependencies, :classes, :classes_and_dependencies, + :type_inference, :method_calls def initialize content super() @content = content @dependencies = [] @@ -15,10 +16,12 @@ @full_class_path = [] @classes_and_dependencies = {} @module_names = [] @complete_class_name = [] @var_propagation = Archruby::Ruby::VarPropagation.new + @type_inference = [] + @method_calls = [] parse end def parse process ruby_parser.parse @content @@ -93,22 +96,76 @@ end def process_call exp _, receiver, method_name, *args = exp process receiver - if receiver && (receiver[0] == :const || receiver[0] == :colon2) if @variables @var_propagation.push @variables.last, exp.line, @dependencies.last end end + build_type_inference(receiver, method_name, args, exp.line) args.map! {|sub_tree| process sub_tree} end + def build_call_history receiver, method_name, params_name + @method_calls << { + :class => @classes.last, + :method => @current_method_name, + :method_arguments => @current_arguments, + :class_call => receiver, + :method_call => method_name, + :method_call_params => params_name + } + end + + def build_type_inference receiver, method_name, params, line_num + if !@local_types.nil? && receiver && receiver[0] == :lvar + receiver = @local_types[receiver[1]] + params_name = [] + deps = [] + params.each do |param| + if param[0] == :lvar + params_name << param[1] + type_inference = TypeInferenceDep.new( + :class_source => @classes.last, + :class_dep => @local_types[param[1]], + :line_source_num => line_num + ) + deps << type_inference + elsif param[0] == :call + process param + type_inference = TypeInferenceDep.new( + :class_source => @classes.last, + :class_dep => @dependencies.last, + :line_source_num => line_num + ) + deps << type_inference + end + end + build_call_history(receiver, method_name, params_name) + @type_inference << { + :class_name => receiver, + :method_name => method_name, + :dep => deps + } if deps.size >= 1 + end + end + + def extract_arguments arguments + _, *arg_vars = arguments + if arg_vars[0].class == Symbol + @current_arguments = arg_vars + end + end + def process_defn exp @variables = [] + @local_types = {} _, method_name, method_arguments, *args = exp + @current_method_name = method_name + extract_arguments(method_arguments) process method_arguments args.map! {|sub_tree| process sub_tree} @var_propagation.vars.each do |var| var = var[var.keys.first] if var[:type] @@ -119,15 +176,21 @@ end end end @var_propagation = Archruby::Ruby::VarPropagation.new @variables = [] + @current_method_name = nil + @current_arguments = nil end def process_lasgn exp _, variable_name, *args = exp + const_access = args[0][0] == :call unless args[0].nil? @variables.push(variable_name) if @variables args.map! {|sub_tree| process sub_tree} + if @local_types.class == Hash && const_access + @local_types[variable_name] = @dependencies.last + end end def process_lit exp _, value = exp end