use factory functions consistently to create instructions
This commit is contained in:
parent
4cf732d395
commit
9cf56b3aa6
@ -7,7 +7,7 @@ module Register
|
|||||||
# so it is responsible for initial setup
|
# so it is responsible for initial setup
|
||||||
def __init__ context
|
def __init__ context
|
||||||
compiler = Typed::MethodCompiler.new.create_method(:Kernel,:__init__ )
|
compiler = Typed::MethodCompiler.new.create_method(:Kernel,:__init__ )
|
||||||
new_start = Label.new("__init__ start" , "__init__" )
|
new_start = Register.label("__init__ start" , "__init__" )
|
||||||
compiler.method.instructions = new_start
|
compiler.method.instructions = new_start
|
||||||
compiler.set_current new_start
|
compiler.set_current new_start
|
||||||
|
|
||||||
@ -17,11 +17,11 @@ module Register
|
|||||||
message_ind = Register.resolve_to_index( :space , :first_message )
|
message_ind = Register.resolve_to_index( :space , :first_message )
|
||||||
compiler.add_code Register.slot_to_reg( "__init__ load 1st message" , space_reg , message_ind , :message)
|
compiler.add_code Register.slot_to_reg( "__init__ load 1st message" , space_reg , message_ind , :message)
|
||||||
compiler.add_code Register.reg_to_slot( "__init__ store Space in message", space_reg , :message , :receiver)
|
compiler.add_code Register.reg_to_slot( "__init__ store Space in message", space_reg , :message , :receiver)
|
||||||
exit_label = Label.new("_exit_label for __init__" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
exit_label = Register.label("_exit_label for __init__" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||||
ret_tmp = compiler.use_reg(:Label)
|
ret_tmp = compiler.use_reg(:Label)
|
||||||
compiler.add_code Register.load_constant("__init__ load return", exit_label , ret_tmp)
|
compiler.add_code Register.load_constant("__init__ load return", exit_label , ret_tmp)
|
||||||
compiler.add_code Register.reg_to_slot("__init__ store return", ret_tmp , :message , :return_address)
|
compiler.add_code Register.reg_to_slot("__init__ store return", ret_tmp , :message , :return_address)
|
||||||
compiler.add_code FunctionCall.new( "__init__ issue call" , Register.machine.space.get_main )
|
compiler.add_code Register.function_call( "__init__ issue call" , Register.machine.space.get_main )
|
||||||
compiler.add_code exit_label
|
compiler.add_code exit_label
|
||||||
emit_syscall( compiler , :exit )
|
emit_syscall( compiler , :exit )
|
||||||
return compiler.method
|
return compiler.method
|
||||||
@ -38,7 +38,7 @@ module Register
|
|||||||
compiler.add_code Syscall.new("emit_syscall(#{name})", name )
|
compiler.add_code Syscall.new("emit_syscall(#{name})", name )
|
||||||
restore_message(compiler)
|
restore_message(compiler)
|
||||||
return unless (@clazz and @method)
|
return unless (@clazz and @method)
|
||||||
compiler.add_code Label.new( "#{@clazz.name}.#{@message.name}" , "return_syscall" )
|
compiler.add_code Register.label( "#{@clazz.name}.#{@message.name}" , "return_syscall" )
|
||||||
end
|
end
|
||||||
|
|
||||||
# save the current message, as the syscall destroys all context
|
# save the current message, as the syscall destroys all context
|
||||||
|
@ -14,7 +14,7 @@ module Register
|
|||||||
source = "get_internal_word"
|
source = "get_internal_word"
|
||||||
me , index = self_and_int_arg(compiler,source)
|
me , index = self_and_int_arg(compiler,source)
|
||||||
# reduce me to me[index]
|
# reduce me to me[index]
|
||||||
compiler.add_code SlotToReg.new( source , me , index , me)
|
compiler.add_code Register.slot_to_reg( source , me , index , me)
|
||||||
# and put it back into the return value
|
# and put it back into the return value
|
||||||
compiler.add_code Register.reg_to_slot( source , me , :message , :return_value)
|
compiler.add_code Register.reg_to_slot( source , me , :message , :return_value)
|
||||||
return compiler.method
|
return compiler.method
|
||||||
@ -29,7 +29,7 @@ module Register
|
|||||||
value = load_int_arg_at(compiler,source , 2)
|
value = load_int_arg_at(compiler,source , 2)
|
||||||
|
|
||||||
# do the set
|
# do the set
|
||||||
compiler.add_code RegToSlot.new( source , value , me , index)
|
compiler.add_code Register.reg_to_slot( source , value , me , index)
|
||||||
return compiler.method
|
return compiler.method
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@ module Register
|
|||||||
source = "get_internal_byte"
|
source = "get_internal_byte"
|
||||||
me , index = self_and_int_arg(compiler,source)
|
me , index = self_and_int_arg(compiler,source)
|
||||||
# reduce me to me[index]
|
# reduce me to me[index]
|
||||||
compiler.add_code ByteToReg.new( source , me , index , me)
|
compiler.add_code Register.byte_to_reg( source , me , index , me)
|
||||||
# and put it back into the return value
|
# and put it back into the return value
|
||||||
compiler.add_code Register.reg_to_slot( source , me , :message , :return_value)
|
compiler.add_code Register.reg_to_slot( source , me , :message , :return_value)
|
||||||
return compiler.method
|
return compiler.method
|
||||||
@ -41,7 +41,7 @@ module Register
|
|||||||
me , index = self_and_int_arg(compiler,source)
|
me , index = self_and_int_arg(compiler,source)
|
||||||
value = load_int_arg_at(compiler , source , 2 )
|
value = load_int_arg_at(compiler , source , 2 )
|
||||||
# do the set
|
# do the set
|
||||||
compiler.add_code RegToByte.new( source , value , me , index)
|
compiler.add_code Register.reg_to_byte( source , value , me , index)
|
||||||
return compiler.method
|
return compiler.method
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -12,9 +12,9 @@ module Register
|
|||||||
# Produce a ByteToReg instruction.
|
# Produce a ByteToReg instruction.
|
||||||
# from and to are translated (from symbol to register if neccessary)
|
# from and to are translated (from symbol to register if neccessary)
|
||||||
# but index is left as is.
|
# but index is left as is.
|
||||||
# def self.byte_to_reg source , array , index , to
|
def self.byte_to_reg( source , array , index , to)
|
||||||
# from = resolve_to_register from
|
array = resolve_to_register( array)
|
||||||
# to = resolve_to_register to
|
to = resolve_to_register( to)
|
||||||
# ByteToReg.new( source , array , index , to)
|
ByteToReg.new( source , array , index , to)
|
||||||
# end
|
end
|
||||||
end
|
end
|
||||||
|
@ -4,7 +4,7 @@ module Register
|
|||||||
# assembly takes care of the rest (ie getting the address)
|
# assembly takes care of the rest (ie getting the address)
|
||||||
|
|
||||||
class FunctionCall < Instruction
|
class FunctionCall < Instruction
|
||||||
def initialize source , method
|
def initialize( source , method )
|
||||||
super(source)
|
super(source)
|
||||||
@method = method
|
@method = method
|
||||||
end
|
end
|
||||||
@ -15,13 +15,17 @@ module Register
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def self.function_call( source , method )
|
||||||
|
Register::FunctionCall.new( source , method )
|
||||||
|
end
|
||||||
|
|
||||||
def self.issue_call( compiler , callee )
|
def self.issue_call( compiler , callee )
|
||||||
return_label = Label.new("_return_label #{callee.name}" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
return_label = Register.label("_return_label #{callee.name}" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||||
ret_tmp = compiler.use_reg(:Label)
|
ret_tmp = compiler.use_reg(:Label)
|
||||||
compiler.add_code Register.load_constant("#{callee.name} load ret", return_label , ret_tmp)
|
compiler.add_code Register.load_constant("#{callee.name} load ret", return_label , ret_tmp)
|
||||||
compiler.add_code Register.reg_to_slot("#{callee.name} store ret", ret_tmp , :new_message , :return_address)
|
compiler.add_code Register.reg_to_slot("#{callee.name} store ret", ret_tmp , :new_message , :return_address)
|
||||||
compiler.add_code Register.transfer("#{callee.name} move new message", Register.new_message_reg , Register.message_reg )
|
compiler.add_code Register.transfer("#{callee.name} move new message", Register.new_message_reg , Register.message_reg )
|
||||||
compiler.add_code FunctionCall.new( "#{callee.name} call" , callee )
|
compiler.add_code Register.function_call( "#{callee.name} call" , callee )
|
||||||
compiler.add_code return_label
|
compiler.add_code return_label
|
||||||
compiler.add_code Register.transfer("#{callee.name} remove new message", Register.message_reg , Register.new_message_reg )
|
compiler.add_code Register.transfer("#{callee.name} remove new message", Register.message_reg , Register.new_message_reg )
|
||||||
compiler.add_code Register.slot_to_reg("#{callee.name} restore message" , :new_message , :caller , :message )
|
compiler.add_code Register.slot_to_reg("#{callee.name} restore message" , :new_message , :caller , :message )
|
||||||
|
@ -4,7 +4,7 @@ module Register
|
|||||||
# register and index specify where the return address is stored
|
# register and index specify where the return address is stored
|
||||||
|
|
||||||
class FunctionReturn < Instruction
|
class FunctionReturn < Instruction
|
||||||
def initialize source , register , index
|
def initialize( source , register , index)
|
||||||
super(source)
|
super(source)
|
||||||
@register = register
|
@register = register
|
||||||
@index = index
|
@index = index
|
||||||
@ -14,6 +14,9 @@ module Register
|
|||||||
def to_s
|
def to_s
|
||||||
"FunctionReturn: #{register} [#{index}]"
|
"FunctionReturn: #{register} [#{index}]"
|
||||||
end
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def self.function_return( source , register , index)
|
||||||
|
FunctionReturn.new( source , register , index)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -8,7 +8,7 @@ module Register
|
|||||||
#
|
#
|
||||||
|
|
||||||
class Label < Instruction
|
class Label < Instruction
|
||||||
def initialize source , name , nekst = nil
|
def initialize( source , name , nekst = nil)
|
||||||
super(source , nekst)
|
super(source , nekst)
|
||||||
@name = name
|
@name = name
|
||||||
end
|
end
|
||||||
@ -77,4 +77,8 @@ module Register
|
|||||||
super
|
super
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def self.label( source , name , nekst = nil)
|
||||||
|
Label.new( source , name , nekst = nil)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
@ -11,11 +11,11 @@ module Register
|
|||||||
# Produce a RegToByte instruction.
|
# Produce a RegToByte instruction.
|
||||||
# from and to are translated (from symbol to register if neccessary)
|
# from and to are translated (from symbol to register if neccessary)
|
||||||
# but index is left as is.
|
# but index is left as is.
|
||||||
# def self.reg_to_byte source , from , to , index
|
def self.reg_to_byte( source , from , to , index)
|
||||||
# from = resolve_to_register from
|
from = resolve_to_register from
|
||||||
# index = resolve_to_index( to , index)
|
index = resolve_to_index( to , index)
|
||||||
# to = resolve_to_register to
|
to = resolve_to_register to
|
||||||
# RegToByte.new( source, from , to , index)
|
RegToByte.new( source, from , to , index)
|
||||||
# end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
@ -105,7 +105,7 @@ module Register
|
|||||||
when :new_message
|
when :new_message
|
||||||
return new_message_reg
|
return new_message_reg
|
||||||
else
|
else
|
||||||
raise "not recognized register reference #{reference}"
|
raise "not recognized register reference #{reference} #{reference.class}"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -133,11 +133,11 @@ module Typed
|
|||||||
def init_method
|
def init_method
|
||||||
source = "_init_method"
|
source = "_init_method"
|
||||||
name = "#{method.for_type.name}.#{method.name}"
|
name = "#{method.for_type.name}.#{method.name}"
|
||||||
@method.instructions = Register::Label.new(source, name)
|
@method.instructions = Register.label(source, name)
|
||||||
@current = enter = method.instructions
|
@current = enter = method.instructions
|
||||||
add_code Register::Label.new( source, "return #{name}")
|
add_code Register.label( source, "return #{name}")
|
||||||
#load the return address into pc, affecting return. (other cpus have commands for this, but not arm)
|
#load the return address into pc, affecting return. (other cpus have commands for this, but not arm)
|
||||||
add_code Register::FunctionReturn.new( source , Register.message_reg , Register.resolve_to_index(:message , :return_address) )
|
add_code Register.function_return( source , Register.message_reg , Register.resolve_to_index(:message , :return_address) )
|
||||||
@current = enter
|
@current = enter
|
||||||
self
|
self
|
||||||
end
|
end
|
||||||
|
@ -21,7 +21,7 @@ module Typed
|
|||||||
reset_regs
|
reset_regs
|
||||||
process(statement.condition)
|
process(statement.condition)
|
||||||
branch_class = Object.const_get "Register::Is#{statement.branch_type.capitalize}"
|
branch_class = Object.const_get "Register::Is#{statement.branch_type.capitalize}"
|
||||||
true_block = Register::Label.new(statement, "if_true")
|
true_block = Register.label(statement, "if_true")
|
||||||
add_code branch_class.new( statement.condition , true_block )
|
add_code branch_class.new( statement.condition , true_block )
|
||||||
return true_block
|
return true_block
|
||||||
end
|
end
|
||||||
@ -33,7 +33,7 @@ module Typed
|
|||||||
def compile_if_false( statement )
|
def compile_if_false( statement )
|
||||||
reset_regs
|
reset_regs
|
||||||
process(statement.if_false) if statement.if_false.statements
|
process(statement.if_false) if statement.if_false.statements
|
||||||
merge = Register::Label.new(statement , "if_merge")
|
merge = Register.label(statement , "if_merge")
|
||||||
add_code Register::Branch.new(statement.if_false, merge )
|
add_code Register::Branch.new(statement.if_false, merge )
|
||||||
merge
|
merge
|
||||||
end
|
end
|
||||||
|
@ -22,13 +22,13 @@ module Typed
|
|||||||
private
|
private
|
||||||
|
|
||||||
def compile_while_preamble( statement )
|
def compile_while_preamble( statement )
|
||||||
condition_label = Register::Label.new(statement.condition , "condition_label")
|
condition_label = Register.label(statement.condition , "condition_label")
|
||||||
# unconditionally branch to the condition upon entering the loop
|
# unconditionally branch to the condition upon entering the loop
|
||||||
add_code Register::Branch.new(statement.condition , condition_label)
|
add_code Register::Branch.new(statement.condition , condition_label)
|
||||||
condition_label
|
condition_label
|
||||||
end
|
end
|
||||||
def compile_while_body( statement )
|
def compile_while_body( statement )
|
||||||
start = Register::Label.new(statement , "while_start" )
|
start = Register.label(statement , "while_start" )
|
||||||
add_code start
|
add_code start
|
||||||
reset_regs
|
reset_regs
|
||||||
process(statement.statements)
|
process(statement.statements)
|
||||||
|
@ -81,7 +81,7 @@ class TestLogic < MiniTest::Test
|
|||||||
end
|
end
|
||||||
|
|
||||||
def label pos = 0x22
|
def label pos = 0x22
|
||||||
l = Register::Label.new("some" , "Label")
|
l = Register.label("some" , "Label")
|
||||||
l.position = pos
|
l.position = pos
|
||||||
l
|
l
|
||||||
end
|
end
|
||||||
|
Loading…
Reference in New Issue
Block a user