rubyx/test/soml/helper.rb
Torsten Ruger 22117035e0 fix last failing tests
historic moment: all the test (currently 56) work on the arm too
2015-11-20 14:37:26 +02:00

90 lines
2.9 KiB
Ruby

require_relative '../helper'
require "register/interpreter"
require "rye"
Rye::Cmd.add_command :ld, '/usr/bin/ld'
Rye::Cmd.add_command :aout, './a.out'
# machinery to run a soml program in 2 ways
# - first by running it through the interpreter
# - second by assembling to arm , pushing the binary to a remote machine and executing it there
#
# The second obviously takes a fair bit of time so it's only done when an REMOTE_PI is set
# REMOTE_PI has to be set to user@machine:port or it will default to an emulator
# the minimum is REMOTE_PI=username , and off course ssh keys have to be set up
# btw can't test with ruby on a PI as code creation only works on 64bit
# that's because ruby nibbles 2 bits from a word, and soml code doesn't work around that
module RuntimeTests
def setup
@stdout = ""
end
def load_program
@machine = Register.machine.boot
Soml::Compiler.load_parfait
@machine.parse_and_compile main()
@machine.collect
end
def check ret = nil
load_program
interpreter = Register::Interpreter.new
interpreter.start @machine.init
count = 0
begin
count += 1
#puts interpreter.instruction
interpreter.tick
end while( ! interpreter.instruction.nil?)
assert_equal @stdout , interpreter.stdout , "stdout wrong locally"
if ret
assert_equal Parfait::Message , interpreter.get_register(:r0).class
assert_equal ret , interpreter.get_register(:r0).return_value , "exit wrong #{@string_input}"
end
check_remote ret
interpreter
end
def connected
return false if ENV["REMOTE_PI"].nil? or (ENV["REMOTE_PI"] == "")
return @@conn if defined?(@@conn)
puts "remote " + ENV["REMOTE_PI"]
user , rest = ENV["REMOTE_PI"].split("@")
machine , port = rest.to_s.split(":")
@@conn = Rye::Box.new(machine || "localhost" , :port => (port || 2222) , :user => (user || "pi"))
end
def check_remote ret_val
return unless box = connected
load_program
file = write_object_file
print "\nfile #{file} "
r_file = file.sub("./" , "salama/")
box.file_upload file , r_file
box.ld "-N", r_file
begin #need to rescue here as rye throws if no return 0
ret = box.aout # and we use return to mean something
rescue Rye::Err => e # so it's basically never 0
ret = e.rap
end
assert_equal @stdout , ret.stdout.join , "remote std was #{ret.stdout}" if @stdout
assert_equal "" , ret.stderr.join , "remote had error"
if ret_val
ret_val &= 0xFF # don't knwo why exit codes are restricted but there you are
assert_equal ret_val , ret.exit_status.to_i , "remote exit failed for #{@string_input}"
end
end
def write_object_file
file_name = caller(3).first.split("in ").last.chop.sub("`","")
return if file_name.include?("run")
file_name = "./tmp/" + file_name + ".o"
Register.machine.translate_arm
writer = Elf::ObjectWriter.new
writer.save file_name
file_name
end
end