class Bpl::Unrolling
Public Instance Methods
run!(program)
click to toggle source
# File lib/bpl/passes/transformation/unrolling.rb, line 38 def run! program loop_identification.loops.each do |head, looop| looop.to_a.last.insert_after(*unroll(head, looop, bound)) looop.each(&:remove) invalidates :all end end
unroll(head, looop, count)
click to toggle source
# File lib/bpl/passes/transformation/unrolling.rb, line 11 def unroll(head, looop, count) names = Set.new(looop.map(&:names).flatten) blocks = (count+1).times.map {looop.map(&:copy)} blocks.each_with_index do |bs, i| bs.each do |b| b.instance_variable_set("@names", b.names.map {|n| "#{n}.unroll.#{i}"}) b.each do |id| if id.is_a?(LabelIdentifier) && names.include?(id.name) if id.name == head.name && i < count id.replace_with(LabelIdentifier.new(name: "#{id}.unroll.#{i+1}")) elsif id.name == head.name id.parent.parent.replace_children(:statements, bpl("assume false;")) else id.replace_with(LabelIdentifier.new(name: "#{id}.unroll.#{i}")) end end end end end head.bindings.each do |id| id.replace_with(LabelIdentifier.new(name: "#{id.name}.unroll.0")) end blocks.flatten end