8a81d41d5e
Also pass the source into the compile method. This way compiler can be reused for subsequent compile. Does remove some double boots, but no major time save
71 lines
2.3 KiB
Ruby
71 lines
2.3 KiB
Ruby
require_relative '../helper'
|
|
|
|
module Risc
|
|
module Statements
|
|
|
|
def setup
|
|
end
|
|
|
|
def preamble
|
|
[ Label ]
|
|
end
|
|
def postamble
|
|
[Label, SlotToReg, SlotToReg, RegToSlot, LoadConstant ,
|
|
SlotToReg, RegToSlot, RegToSlot, SlotToReg, SlotToReg,
|
|
SlotToReg , FunctionReturn, Label]
|
|
end
|
|
# test hack to in place change object type
|
|
def add_space_field(name,type)
|
|
class_type = Parfait.object_space.get_type_by_class_name(:Space)
|
|
class_type.send(:private_add_instance_variable, name , type)
|
|
end
|
|
def produce_body
|
|
produced = produce_instructions
|
|
preamble.each{ produced = produced.next }
|
|
produced
|
|
end
|
|
def as_test_main
|
|
"class Test; def main(arg);#{@input};end;end"
|
|
end
|
|
def produce_instructions
|
|
assert @expect , "No output given"
|
|
linker = RubyX::RubyXCompiler.new.ruby_to_risc(as_test_main,:interpreter)
|
|
compiler = linker.assemblers.find{|c| c.callable.name == :main and c.callable.self_type.object_class.name == :Test}
|
|
compiler.instructions
|
|
end
|
|
def check_nil
|
|
produced = produce_instructions
|
|
compare_instructions( produced , @expect)
|
|
end
|
|
def check_return
|
|
was = check_nil
|
|
raise was if was
|
|
test = Parfait.object_space.get_class_by_name :Test
|
|
test.instance_type.get_method :main
|
|
end
|
|
def compare_instructions( instruction , expect )
|
|
index = 0
|
|
all = instruction.to_arr
|
|
full_expect = preamble + expect + postamble
|
|
#full_expect = expect
|
|
begin
|
|
should = full_expect[index]
|
|
return "No instruction at #{index-1}\n#{should(all)[0..100]}" unless should
|
|
return "Expected at #{index-1}\n#{should(all)} was #{instruction.to_s[0..100]}" unless instruction.class == should
|
|
#puts "#{index-1}:#{instruction.to_s}" if (index > preamble.length) and (index + postamble.length <= full_expect.length)
|
|
index += 1
|
|
instruction = instruction.next
|
|
end while( instruction )
|
|
nil
|
|
end
|
|
def should( all )
|
|
preamble.each {all.shift}
|
|
postamble.each {all.pop}
|
|
str = all.collect{|i| i.class.name}.join(", ").gsub("Risc::","")
|
|
str = "[#{str}]"
|
|
all = str.split(",").each_slice(5).collect { |line| " " + line.join(",")}
|
|
all.join(",\n")
|
|
end
|
|
end
|
|
end
|