diff --git a/.travis.yml b/.travis.yml index b3246924..593ba35c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,8 +1,8 @@ before_install: - sudo apt-get install -y qemu - sudo apt-get install -y binutils-arm-linux-gnueabi + - gem install bundler --version '2.0.1' language: ruby -before_install: gem install bundler --version '2.0.1' script: - qemu-arm -version - arm-linux-gnu-ld -v diff --git a/lib/rubyx/rubyxc.rb b/lib/rubyx/rubyxc.rb index 7aee2ea2..ec65ddd0 100644 --- a/lib/rubyx/rubyxc.rb +++ b/lib/rubyx/rubyxc.rb @@ -91,15 +91,14 @@ class RubyXC < Thor def execute(file) outfile = compile(file) - system "arm-linux-gnueabihf-ld -N #{outfile}" + system "arm-linux-gnueabi-ld -N #{outfile}" puts "Linked ok, now running #{file}" - system "qemu-arm ./a.out" + system "qemu-arm ./a.out ; echo $?" end private def extract_options opt = { factory: options[:parfait] || 1024 } - puts opt return {parfait: opt} end diff --git a/test/mains/test_arm.rb b/test/mains/test_arm.rb index d72ace61..4fe96d22 100644 --- a/test/mains/test_arm.rb +++ b/test/mains/test_arm.rb @@ -5,21 +5,13 @@ require 'net/scp' module Mains class TestArm < MiniTest::Test - DEBUG = true - def self.user - ENV["ARM_USER"] || "pi" - end - def self.port - ENV["ARM_PORT"] || 2222 - end + DEBUG = false # runnable_methods is called by minitest to determine which tests to run def self.runnable_methods all = Dir["test/mains/source/*_*.rb"] tests =[] - host = ENV["ARM_HOST"] - return tests unless host - ssh = Net::SSH.start(host, user , port: port ) + return tests unless has_qemu all.each do |file_name| fullname = file_name.split("/").last.split(".").first name , stdout , exit_code = fullname.split("_") @@ -27,8 +19,7 @@ module Mains input = File.read(file_name) tests << method_name self.send(:define_method, method_name ) do - compile( input , name , ssh.scp) - out , code = run_ssh(name , ssh) + out , code = run_code(input , name) assert_equal stdout , out , "Wrong stdout #{name}" assert_equal exit_code , code.to_s , "Wrong exit code #{name}" end @@ -36,53 +27,33 @@ module Mains tests end - def compile(input , file , scp) - Risc.boot! - puts "Compiling test/#{file}.o" if DEBUG - RubyX::RubyXCompiler.ruby_to_binary( input ) - writer = Elf::ObjectWriter.new(Risc.machine) - writer.save "test/#{file}.o" - object_file = "/tmp/#{file}.o" - puts "Copying test/#{file}.o to #{object_file}" if DEBUG - scp.upload! "test/#{file}.o", object_file + def self.has_qemu + `qemu-arm -version` + return false unless $?.exitstatus == 0 + `arm-linux-gnu-ld -v` + return false unless $?.exitstatus == 0 + true end - def run_ssh( file , ssh) - binary_file = "/tmp/#{file}" - object_file = binary_file + ".o" - puts "Linking #{object_file}" if DEBUG - stdout , exit_code = ssh_exec!(ssh , "ld -N -o #{binary_file} #{object_file}") - assert_equal 0 , exit_code , "Linking #{binary_file} failed" - puts "Running #{binary_file}" if DEBUG - stdout , exit_code = ssh_exec!(ssh , binary_file) + def run_code(input , name ) + puts "Compiling #{name}.o" if DEBUG + + linker = ::RubyX::RubyXCompiler.new({}).ruby_to_binary( input , :arm ) + writer = Elf::ObjectWriter.new(linker) + + writer.save "mains.o" + + puts "Linking #{name}" if DEBUG + + `arm-linux-gnu-ld -N mains.o` + assert_equal 0 , $?.exitstatus , "Linking #{name} failed #{$?}" + + puts "Running #{name}" if DEBUG + stdout = `qemu-arm ./a.out` + exit_code = $?.exitstatus puts "Result #{stdout} #{exit_code}" if DEBUG return stdout , exit_code end - def ssh_exec!(ssh, command) - stdout_data = "" - exit_code = nil - ssh.open_channel do |channel| - channel.exec(command) do |ch, success| - unless success - raise "FAILED: couldn't execute command (ssh.channel.exec)" - end - channel.on_data do |c,data| - stdout_data+=data - end - channel.on_extended_data do |c,type,data| - raise "#{ssh} received stderr #{data}" - end - channel.on_request("exit-status") do |c,data| - exit_code = data.read_long - end - channel.on_request("exit-signal") do |c, data| - raise "#{ssh} received signal #{data.read_long}" - end - end - end - ssh.loop - [stdout_data, exit_code] - end end end