diff --git a/lib/mom/instruction/dynamic_call.rb b/lib/mom/instruction/dynamic_call.rb index 9280223b..7e320223 100644 --- a/lib/mom/instruction/dynamic_call.rb +++ b/lib/mom/instruction/dynamic_call.rb @@ -27,10 +27,15 @@ module Mom def to_risc(compiler) compiler.add_constant( @cache_entry ) reg = compiler.use_reg( :Object ) - call = Risc.load_constant( self , @cache_entry , reg ) + return_label = Risc::Label.new(self,"continue_#{object_id}") + save_return = SlotLoad.new([:message,:next_message,:return_address],[return_label],self) + moves = save_return.to_risc(compiler) + moves << Risc.slot_to_reg(self, :message , :next_message , Risc.message_reg) + moves << Risc.load_constant( self , @cache_entry , reg ) method_index = Risc.resolve_to_index(:cache_entry , :cached_method) - call << Risc::SlotToReg.new( self , reg ,method_index, reg) - call << Risc::DynamicJump.new(self, reg ) + moves << Risc::SlotToReg.new( self , reg ,method_index, reg) + moves << Risc::DynamicJump.new(self, reg ) + moves << return_label end end diff --git a/lib/mom/instruction/simple_call.rb b/lib/mom/instruction/simple_call.rb index 29c79279..b3c2e55a 100644 --- a/lib/mom/instruction/simple_call.rb +++ b/lib/mom/instruction/simple_call.rb @@ -25,8 +25,10 @@ module Mom save_return = SlotLoad.new([:message,:next_message,:return_address],[return_label],self) moves = save_return.to_risc(compiler) moves << Risc.slot_to_reg(self, :message , :next_message , Risc.message_reg) + moves << Risc.load_constant(self , method.binary , jump_address) moves << Risc::FunctionCall.new(self, method ,jump_address) + moves << return_label end diff --git a/test/mom/send/test_send_dynamic.rb b/test/mom/send/test_send_dynamic.rb index d9378ff5..a9a4dad9 100644 --- a/test/mom/send/test_send_dynamic.rb +++ b/test/mom/send/test_send_dynamic.rb @@ -19,7 +19,8 @@ module Risc RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, RegToSlot, SlotToReg, RegToSlot, SlotToReg, SlotToReg, SlotToReg, RegToSlot, - LoadConstant, SlotToReg, DynamicJump] + LoadConstant, SlotToReg, RegToSlot, SlotToReg, LoadConstant, + SlotToReg, DynamicJump, Label] end def test_send_instructions @@ -37,7 +38,7 @@ module Risc end def test_function_call produced = produce_body - assert_equal DynamicJump , produced.next(62).class + assert_equal DynamicJump , produced.next(66).class end def test_cache_check produced = produce_body diff --git a/test/risc/interpreter/test_dynamic_call.rb b/test/risc/interpreter/test_dynamic_call.rb index 2474e653..bcd68d6b 100644 --- a/test/risc/interpreter/test_dynamic_call.rb +++ b/test/risc/interpreter/test_dynamic_call.rb @@ -5,7 +5,7 @@ module Risc include Ticker def setup - @string_input = as_main("a = 15 ; return a.div10") + @string_input = as_main("a = 5 ; return a.mod4") super end @@ -22,24 +22,23 @@ module Risc Label, LoadConstant, SlotToReg, OperatorInstruction, IsZero, SlotToReg, OperatorInstruction, IsZero, SlotToReg, Branch, Label, LoadConstant, SlotToReg, OperatorInstruction, IsZero, + SlotToReg, OperatorInstruction, IsZero, SlotToReg, Branch, + Label, LoadConstant, SlotToReg, OperatorInstruction, IsZero, SlotToReg, OperatorInstruction, IsZero, Label, RegToSlot, Label, LoadConstant, SlotToReg, LoadConstant, SlotToReg, RegToSlot, RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, RegToSlot, SlotToReg, RegToSlot, SlotToReg, SlotToReg, SlotToReg, - RegToSlot, LoadConstant, SlotToReg, DynamicJump, Label, - SlotToReg, SlotToReg, SlotToReg, SlotToReg, SlotToReg, - SlotToReg, LoadData, OperatorInstruction, LoadData, OperatorInstruction, - OperatorInstruction, LoadData, Transfer, OperatorInstruction, OperatorInstruction, - LoadData, Transfer, OperatorInstruction, OperatorInstruction, LoadData, - Transfer, OperatorInstruction, OperatorInstruction, LoadData, OperatorInstruction, - LoadData, Transfer, OperatorInstruction, OperatorInstruction, Transfer, - LoadData, OperatorInstruction, LoadData, OperatorInstruction, OperatorInstruction, - LoadConstant, SlotToReg, SlotToReg, RegToSlot, RegToSlot, + RegToSlot, LoadConstant, SlotToReg, RegToSlot, SlotToReg, + LoadConstant, SlotToReg, DynamicJump, Label, SlotToReg, + SlotToReg, LoadData, OperatorInstruction, LoadConstant, SlotToReg, + SlotToReg, RegToSlot, RegToSlot, RegToSlot, SlotToReg, + SlotToReg, RegToSlot, SlotToReg, SlotToReg, FunctionReturn, + SlotToReg, SlotToReg, RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, SlotToReg, RegToSlot, SlotToReg, SlotToReg, FunctionReturn, Transfer, Syscall, NilClass] assert_equal Parfait::Integer , get_return.class - #assert_equal 1 , get_return.value + assert_equal 1 , get_return.value end def test_call_main @@ -53,17 +52,17 @@ module Risc assert_equal Parfait::CacheEntry , call_ins.constant.class end - def est_dyn - cal = main_ticks(76) + def test_dyn + cal = main_ticks(98) assert_equal DynamicJump , cal.class end #should end in exit, but doesn't, becasue resolve never returns - def ttest_sys - sys = ticks(20) + def test_sys + sys = main_ticks(129) assert_equal Syscall , sys.class end - def ttest_return - ret = ticks(18) + def test_return + ret = main_ticks(127) assert_equal FunctionReturn , ret.class link = @interpreter.get_register( ret.register ) assert_equal Label , link.class