hacking method not found

was using exit, since raise is not implemented. This was ambiguous as all programs exit.
Using :died as special kernel code and bending it, and reporting it in interpreter.
This commit is contained in:
Torsten Rüger 2019-09-09 11:47:37 +03:00
parent 7334e72458
commit 0ae7c5d8aa
6 changed files with 22 additions and 7 deletions

View File

@ -139,10 +139,12 @@ module Arm
end
def translate_Syscall( code )
call_codes = { :putstring => 4 , :exit => 1 }
int_code = call_codes[code.name]
raise "Not implemented syscall, #{code.name}" unless int_code
send( code.name , int_code )
call_codes = { putstring: 4 , exit: 1 }
name = code.name
name = :exit if name == :died
int_code = call_codes[name]
raise "Not implemented syscall, #{name}" unless int_code
send( name , int_code )
end
def putstring( int_code )

View File

@ -65,7 +65,7 @@ module Mom
# temporary, need to raise really.
factory! << Parfait.object_space.get_factory_for(:Integer)
integer_tmp! << factory[:reserve]
Mom::Builtin.emit_syscall( builder , :exit ) #uses integer_tmp
Mom::Builtin.emit_syscall( builder , :died ) #uses integer_tmp
add_code ok_label
cache_entry[:cached_method] << callable_method

View File

@ -245,6 +245,8 @@ module Risc
when :exit
set_instruction(nil)
return false
when :died
raise "Method not found #{@registers[:r0]}"
else
raise "un-implemented syscall #{name}"
end

View File

@ -42,7 +42,7 @@ module Mains
run_all
assert_equal ::Integer , get_return.class , " "
#assert_equal 4 , get_return , " "
assert_equal "hi" , @interpreter.stdout
assert_equal "Space" , @interpreter.stdout
end
end

View File

@ -27,7 +27,7 @@ module Risc
def test_sys
produced = produce_body
assert_equal Syscall , produced.next(29).class
assert_equal :exit , produced.next(29).name
assert_equal :died , produced.next(29).name
end
def test_load_address
produced = produce_body

View File

@ -91,5 +91,16 @@ module Risc
def test_tick_15 #more than a binary code worth
31.times {@interpreter.tick}
end
class TestInterpreterDies < MiniTest::Test
include Ticker
def setup
@string_input = as_main("random.call")
super
end
def test_dies
# no method does syscall :dies that raises
assert_raises {44.times {@interpreter.tick}}
end
end
end
end