rename register to risc
seems to fit the layer much better as we really have a very reduced instruction set
This commit is contained in:
parent
da5823a1a0
commit
aa79e41d1c
16
.reek
16
.reek
@ -6,25 +6,25 @@ DuplicateMethodCall:
|
||||
max_calls: 2
|
||||
FeatureEnvy:
|
||||
exclude:
|
||||
- "Register::Interpreter"
|
||||
- "Register::Assembler"
|
||||
- "Risc::Interpreter"
|
||||
- "Risc::Assembler"
|
||||
- "Arm::Translator"
|
||||
- "Vm::ToCode"
|
||||
TooManyMethods:
|
||||
exclude:
|
||||
- "Register::Interpreter"
|
||||
- "Register::Assembler"
|
||||
- "Risc::Interpreter"
|
||||
- "Risc::Assembler"
|
||||
- "Arm::Translator"
|
||||
- "Vm::ToCode"
|
||||
UtilityFunction:
|
||||
exclude:
|
||||
- "Register::Interpreter"
|
||||
- "Register::Assembler"
|
||||
- "Risc::Interpreter"
|
||||
- "Risc::Assembler"
|
||||
- "Arm::Translator"
|
||||
- "Vm::ToCode"
|
||||
UncommunicativeMethodName:
|
||||
exclude:
|
||||
- "Register::Assembler"
|
||||
- "Register::Interpreter"
|
||||
- "Risc::Assembler"
|
||||
- "Risc::Interpreter"
|
||||
- "Arm::Translator"
|
||||
- "Vm::ToCode"
|
||||
|
@ -31,7 +31,7 @@ the code reads much nicer when they are on the module.
|
||||
|
||||
### Code generators
|
||||
|
||||
Instead of SlotToReg.new( register, index , register) we use Register.slot_to_reg( name , name , name).
|
||||
Instead of SlotToReg.new( register, index , register) we use Risc.slot_to_reg( name , name , name).
|
||||
All names are resolved to registers, or index via Type. More readable code less repetition.
|
||||
As the example shows, in this case the module function name should be the instruction class name.
|
||||
|
||||
|
@ -13,7 +13,7 @@ but not as a language). The idea is to compile ruby to that typed representation
|
||||
|
||||
We use whitequarks parser to parse ruby.
|
||||
|
||||
Processing is roughly: ruby --> Typed --> Register --> Arm --> binary .
|
||||
Processing is roughly: Ruby --> Vm --> Risc --> Arm --> binary .
|
||||
|
||||
|
||||
## Done
|
||||
@ -22,7 +22,7 @@ Some things that are finished, look below for current status / work
|
||||
|
||||
### Typed representation
|
||||
|
||||
The fully typed syntax representation and compiler to the Register level is done.
|
||||
The fully typed syntax representation and compiler to the Risc level is done.
|
||||
It is remodeled after last years system language, which proved the concept and
|
||||
surprised with speed.
|
||||
|
||||
@ -36,7 +36,7 @@ of support is needed to get the system up, and that is [Parfait](http://ruby-x.o
|
||||
### Interpreter
|
||||
|
||||
After doing some debugging on the generated binaries i opted to write an interpreter for the
|
||||
register layer. That way test runs on the interpreter reveal most issues.
|
||||
risc layer. That way test runs on the interpreter reveal most issues.
|
||||
|
||||
### Debugger
|
||||
|
||||
|
@ -55,7 +55,7 @@ module Arm
|
||||
def self.class_for clazz
|
||||
my_module = self.class.name.split("::").first
|
||||
clazz_name = clazz.name.split("::").last
|
||||
if(my_module != Register )
|
||||
if(my_module != Risc )
|
||||
module_class = eval("#{my_module}::#{clazz_name}") rescue nil
|
||||
clazz = module_class if module_class
|
||||
end
|
||||
@ -63,11 +63,11 @@ module Arm
|
||||
end
|
||||
|
||||
#defining the instruction (opcode, symbol) as an given class.
|
||||
# the class is a Register::Instruction derived base class and to create machine specific function
|
||||
# the class is a Risc::Instruction derived base class and to create machine specific function
|
||||
# an actual machine must create derived classes (from this base class)
|
||||
# These instruction classes must follow a naming pattern and take a hash in the contructor
|
||||
# Example, a mov() opcode instantiates a Register::MoveInstruction
|
||||
# for an Arm machine, a class Arm::MoveInstruction < Register::MoveInstruction exists, and it
|
||||
# Example, a mov() opcode instantiates a Risc::MoveInstruction
|
||||
# for an Arm machine, a class Arm::MoveInstruction < Risc::MoveInstruction exists, and it
|
||||
# will be used to define the mov on an arm machine.
|
||||
# This methods picks up that derived class and calls a define_instruction methods that can
|
||||
# be overriden in subclasses
|
||||
|
@ -56,11 +56,11 @@ module Arm
|
||||
def reg r_name
|
||||
code = reg_code r_name
|
||||
raise "no such register #{r_name}" unless code
|
||||
Arm::Register.new(r_name.to_sym , code )
|
||||
Arm::Risc.new(r_name.to_sym , code )
|
||||
end
|
||||
def reg_code r_name
|
||||
raise "double r #{r_name}" if( :rr1 == r_name)
|
||||
if r_name.is_a? ::Register::RegisterValue
|
||||
if r_name.is_a? ::Risc::RiscValue
|
||||
r_name = r_name.symbol
|
||||
end
|
||||
if r_name.is_a? Fixnum
|
||||
@ -93,7 +93,7 @@ module Arm
|
||||
end
|
||||
end
|
||||
|
||||
Register::RegisterValue.class_eval do
|
||||
Risc::RiscValue.class_eval do
|
||||
def reg_no
|
||||
@symbol.to_s[1 .. -1].to_i
|
||||
end
|
||||
|
@ -8,8 +8,8 @@ module Arm
|
||||
|
||||
# swi (SoftWareInterrupt) or system call is how we call the kernel.
|
||||
# in Arm the register layout is different and so we have to place the syscall code into register 7
|
||||
# Registers 0-6 hold the call values as for a normal c call
|
||||
class CallInstruction < Register::Branch
|
||||
# Riscs 0-6 hold the call values as for a normal c call
|
||||
class CallInstruction < Risc::Branch
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
@ -44,7 +44,7 @@ module Arm
|
||||
|
||||
def handle_call(io)
|
||||
case @first
|
||||
when Register::Label
|
||||
when Risc::Label
|
||||
# relative addressing for jumps/calls
|
||||
# but because of the arm "theoretical" 3- stage pipeline,
|
||||
# we have to subtract 2 words (fetch/decode)
|
||||
|
@ -1,5 +1,5 @@
|
||||
module Arm
|
||||
class CompareInstruction < Register::Instruction
|
||||
class CompareInstruction < Risc::Instruction
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
@ -20,19 +20,19 @@ module Arm
|
||||
rn , operand , immediate= @rn , @operand , 1
|
||||
|
||||
arg = @right
|
||||
operand = Register::RegisterValue.new( arg , :Integer) if( arg.is_a? Symbol )
|
||||
operand = Risc::RiscValue.new( arg , :Integer) if( arg.is_a? Symbol )
|
||||
case operand
|
||||
when Numeric
|
||||
operand = arg
|
||||
raise "numeric literal operand to large #{arg.inspect}" unless (arg.fits_u8?)
|
||||
when Symbol , ::Register::RegisterValue
|
||||
when Symbol , ::Risc::RiscValue
|
||||
immediate = 0
|
||||
when Arm::Shift
|
||||
handle_shift
|
||||
else
|
||||
raise "invalid operand argument #{arg.inspect} , #{inspect}"
|
||||
end
|
||||
val = (operand.is_a?(Symbol) or operand.is_a?(::Register::RegisterValue)) ? reg_code(operand) : operand
|
||||
val = (operand.is_a?(Symbol) or operand.is_a?(::Risc::RiscValue)) ? reg_code(operand) : operand
|
||||
val = 0 if val == nil
|
||||
val = shift(val , 0)
|
||||
raise inspect unless reg_code(@rd)
|
||||
@ -64,12 +64,12 @@ module Arm
|
||||
# end
|
||||
#
|
||||
# arg1 = arg.value
|
||||
# if (arg1.is_a?(Register::IntegerConstant))
|
||||
# if (arg1.is_a?(Risc::IntegerConstant))
|
||||
# if (arg1.value >= 32)
|
||||
# raise "cannot shift by more than 31 #{arg1} #{inspect}"
|
||||
# end
|
||||
# shift_imm = arg1.value
|
||||
# elsif (arg1.is_a?(Arm::Register))
|
||||
# elsif (arg1.is_a?(Arm::Risc))
|
||||
# shift_op val |= 0x1;
|
||||
# shift_imm = arg1.number << 1
|
||||
# elsif (arg.type == 'rrx')
|
||||
|
@ -1,5 +1,5 @@
|
||||
module Arm
|
||||
class LogicInstruction < Register::Instruction
|
||||
class LogicInstruction < Risc::Instruction
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
@ -26,7 +26,7 @@ module Arm
|
||||
|
||||
if (right.is_a?(Numeric))
|
||||
operand = handle_numeric(right)
|
||||
elsif (right.is_a?(Symbol) or right.is_a?(::Register::RegisterValue))
|
||||
elsif (right.is_a?(Symbol) or right.is_a?(::Risc::RiscValue))
|
||||
operand = reg_code(right) #integer means the register the integer is in (otherwise constant)
|
||||
immediate = 0 # ie not immediate is register
|
||||
else
|
||||
@ -73,7 +73,7 @@ module Arm
|
||||
unless @extra
|
||||
@extra = 1
|
||||
#puts "RELINK L at #{self.position.to_s(16)}"
|
||||
raise ::Register::LinkException.new("cannot fit numeric literal argument in operand #{right.inspect}")
|
||||
raise ::Risc::LinkException.new("cannot fit numeric literal argument in operand #{right.inspect}")
|
||||
end
|
||||
# now we can do the actual breaking of instruction, by splitting the operand
|
||||
operand = calculate_u8_with_rr( right & 0xFFFFFF00 )
|
||||
@ -87,8 +87,8 @@ module Arm
|
||||
# don't overwrite instance variables, to make assembly repeatable
|
||||
# this also loads constants, which are issued as pc relative adds
|
||||
def determine_operands
|
||||
if( @left.is_a?(Parfait::Object) or @left.is_a?(Register::Label) or
|
||||
(@left.is_a?(Symbol) and !Register::RegisterValue.look_like_reg(@left)))
|
||||
if( @left.is_a?(Parfait::Object) or @left.is_a?(Risc::Label) or
|
||||
(@left.is_a?(Symbol) and !Risc::RiscValue.look_like_reg(@left)))
|
||||
# do pc relative addressing with the difference to the instuction
|
||||
# 8 is for the funny pipeline adjustment (ie pointing to fetch and not execute)
|
||||
right = Positioned.position(@left) - Positioned.position(self) - 8
|
||||
|
@ -2,7 +2,7 @@ module Arm
|
||||
# ADDRESSING MODE 2
|
||||
# Implemented: immediate offset with offset=0
|
||||
|
||||
class MemoryInstruction < Register::Instruction
|
||||
class MemoryInstruction < Risc::Instruction
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
@ -15,7 +15,7 @@ module Arm
|
||||
@attributes[:update_status] = 1 if @attributes[:update_status] == nil
|
||||
@attributes[:condition_code] = :al if @attributes[:condition_code] == nil
|
||||
@operand = 0
|
||||
raise "alert" if right.is_a? Register::Label
|
||||
raise "alert" if right.is_a? Risc::Label
|
||||
@add_offset = @attributes[:add_offset] ? 0 : 1 #U flag
|
||||
@is_load = opcode.to_s[0] == "l" ? 1 : 0 #L (load) flag
|
||||
end
|
||||
@ -25,8 +25,8 @@ module Arm
|
||||
#TODO better test, this operand integer (register) does not work.
|
||||
def assemble(io)
|
||||
arg = @left
|
||||
arg = arg.symbol if( arg.is_a? ::Register::RegisterValue )
|
||||
is_reg = arg.is_a?(::Register::RegisterValue)
|
||||
arg = arg.symbol if( arg.is_a? ::Risc::RiscValue )
|
||||
is_reg = arg.is_a?(::Risc::RiscValue)
|
||||
is_reg = (arg.to_s[0] == "r") if( arg.is_a?(Symbol) and not is_reg)
|
||||
|
||||
raise "invalid operand argument #{arg.inspect} #{inspect}" unless (is_reg )
|
||||
@ -35,7 +35,7 @@ module Arm
|
||||
#not sure about these 2 constants. They produce the correct output for str r0 , r1
|
||||
# but i can't help thinking that that is because they are not used in that instruction and
|
||||
# so it doesn't matter. Will see
|
||||
if (operand.is_a?(Symbol) or operand.is_a?(::Register::RegisterValue))
|
||||
if (operand.is_a?(Symbol) or operand.is_a?(::Risc::RiscValue))
|
||||
val = reg_code(operand)
|
||||
i = 1 # not quite sure about this, but it gives the output of as. read read read.
|
||||
else
|
||||
@ -67,7 +67,7 @@ module Arm
|
||||
def get_operand
|
||||
return @operand unless @right
|
||||
operand = @right
|
||||
operand = operand.symbol if operand.is_a? ::Register::RegisterValue
|
||||
operand = operand.symbol if operand.is_a? ::Risc::RiscValue
|
||||
unless( operand.is_a? Symbol)
|
||||
# TODO test/check/understand: has no effect in current tests
|
||||
# add_offset = (operand < 0) ? 0 : 1
|
||||
|
@ -1,13 +1,13 @@
|
||||
module Arm
|
||||
class MoveInstruction < Register::Instruction
|
||||
class MoveInstruction < Risc::Instruction
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
def initialize to , from , options = {}
|
||||
super(nil)
|
||||
@attributes = options
|
||||
if( from.is_a?(Symbol) and Register::RegisterValue.look_like_reg(from) )
|
||||
from = Register::RegisterValue.new(from , :Integer)
|
||||
if( from.is_a?(Symbol) and Risc::RiscValue.look_like_reg(from) )
|
||||
from = Risc::RiscValue.new(from , :Integer)
|
||||
end
|
||||
@from = from
|
||||
@to = to
|
||||
@ -40,7 +40,7 @@ module Arm
|
||||
case right
|
||||
when Numeric
|
||||
operand = numeric_operand(right)
|
||||
when Register::RegisterValue
|
||||
when Risc::RiscValue
|
||||
operand = reg_code(right)
|
||||
immediate = 0 # ie not immediate is register
|
||||
else
|
||||
@ -72,7 +72,7 @@ module Arm
|
||||
raise "No negatives implemented #{right} " if right < 0
|
||||
unless @extra
|
||||
@extra = 1 # puts "RELINK M at #{self.position.to_s(16)}"
|
||||
raise ::Register::LinkException.new("cannot fit numeric literal argument in operand #{right.inspect}")
|
||||
raise ::Risc::LinkException.new("cannot fit numeric literal argument in operand #{right.inspect}")
|
||||
end
|
||||
# now we can do the actual breaking of instruction, by splitting the operand
|
||||
operand = calculate_u8_with_rr( right & 0xFFFFFF00 )
|
||||
|
@ -1,7 +1,7 @@
|
||||
module Arm
|
||||
# ADDRESSING MODE 4
|
||||
|
||||
class StackInstruction < Register::Instruction
|
||||
class StackInstruction < Risc::Instruction
|
||||
include Constants
|
||||
include Attributed
|
||||
|
||||
|
@ -2,7 +2,7 @@ module Arm
|
||||
class MachineCode
|
||||
|
||||
def function_call into , call
|
||||
raise "Not CallSite #{call.inspect}" unless call.is_a? Register::CallSite
|
||||
raise "Not CallSite #{call.inspect}" unless call.is_a? Risc::CallSite
|
||||
raise "Not linked #{call.inspect}" unless call.function
|
||||
into.add_code call( call.function )
|
||||
raise "No return type for #{call.function.name}" unless call.function.return_type
|
||||
@ -10,13 +10,13 @@ module Arm
|
||||
end
|
||||
|
||||
def main_start context
|
||||
entry = Register::Block.new("main_entry",nil,nil)
|
||||
entry = Risc::Block.new("main_entry",nil,nil)
|
||||
entry.add_code mov( :fp , 0 )
|
||||
entry.add_code call( context.function )
|
||||
entry
|
||||
end
|
||||
def main_exit context
|
||||
exit = Register::Block.new("main_exit",nil,nil)
|
||||
exit = Risc::Block.new("main_exit",nil,nil)
|
||||
syscall(exit , 1)
|
||||
exit
|
||||
end
|
||||
@ -44,7 +44,7 @@ module Arm
|
||||
end
|
||||
|
||||
|
||||
# the number (a Register::integer) is (itself) divided by 10, ie overwritten by the result
|
||||
# the number (a Risc::integer) is (itself) divided by 10, ie overwritten by the result
|
||||
# and the remainder is overwritten (ie an out argument)
|
||||
# not really a function, more a macro,
|
||||
def div10 function, number , remainder
|
||||
@ -69,8 +69,8 @@ module Arm
|
||||
def syscall block , num
|
||||
# This is very arm specific, syscall number is passed in r7,
|
||||
# other arguments like a c call ie 0 and up
|
||||
sys = Register::Integer.new( Register::RegisterValue.new(SYSCALL_REG) )
|
||||
ret = Register::Integer.new( Register::RegisterValue.new(RETURN_REG) )
|
||||
sys = Risc::Integer.new( Risc::RiscValue.new(SYSCALL_REG) )
|
||||
ret = Risc::Integer.new( Risc::RiscValue.new(RETURN_REG) )
|
||||
block.add_code mov( sys , num )
|
||||
block.add_code swi( 0 )
|
||||
#todo should write type into r1 according to syscall
|
||||
|
@ -19,7 +19,7 @@ module Arm
|
||||
# in bytes, so *4
|
||||
# if an instruction is passed in we get the index with index function
|
||||
def arm_index index
|
||||
index = index.index if index.is_a?(Register::Instruction)
|
||||
index = index.index if index.is_a?(Risc::Instruction)
|
||||
raise "index error 0" if index == 0
|
||||
index * 4
|
||||
end
|
||||
@ -31,8 +31,8 @@ module Arm
|
||||
ArmMachine.str( :lr , code.register , arm_index(code) )
|
||||
end
|
||||
|
||||
def translate_RegisterTransfer( code )
|
||||
# Register machine convention is from => to
|
||||
def translate_RiscTransfer( code )
|
||||
# Risc machine convention is from => to
|
||||
# But arm has the receiver/result as the first
|
||||
ArmMachine.mov( code.to , code.from)
|
||||
end
|
||||
@ -77,7 +77,7 @@ module Arm
|
||||
|
||||
def translate_LoadConstant code
|
||||
constant = code.constant
|
||||
if constant.is_a?(Parfait::Object) or constant.is_a?(Symbol) or constant.is_a?(Register::Label)
|
||||
if constant.is_a?(Parfait::Object) or constant.is_a?(Symbol) or constant.is_a?(Risc::Label)
|
||||
return ArmMachine.add( code.register , constant )
|
||||
else
|
||||
return ArmMachine.mov( code.register , constant )
|
||||
@ -146,7 +146,7 @@ module Arm
|
||||
end
|
||||
|
||||
def exit int_code
|
||||
codes = ArmMachine.ldr( :r0 , :r0 , arm_index(Register.resolve_to_index(:Message , :return_value)) )
|
||||
codes = ArmMachine.ldr( :r0 , :r0 , arm_index(Risc.resolve_to_index(:Message , :return_value)) )
|
||||
syscall int_code , codes
|
||||
end
|
||||
|
||||
|
@ -20,7 +20,7 @@ module Elf
|
||||
@text = Elf::TextSection.new(".text")
|
||||
@object.add_section @text
|
||||
|
||||
assembler = Register::Assembler.new(@machine , @objects)
|
||||
assembler = Risc::Assembler.new(@machine , @objects)
|
||||
set_text assembler.write_as_string
|
||||
|
||||
# for debug add labels for labels
|
||||
|
@ -24,7 +24,7 @@ module Parfait
|
||||
end
|
||||
# initialize with length. For now we try to keep all non-parfait (including String) out
|
||||
# String will contain spaces for non-zero length
|
||||
# Register provides methods to create Parfait objects from ruby
|
||||
# Risc provides methods to create Parfait objects from ruby
|
||||
def initialize len
|
||||
super()
|
||||
@char_length = 0
|
||||
|
@ -5,12 +5,12 @@ class String
|
||||
end
|
||||
|
||||
|
||||
require "register/padding"
|
||||
require "register/positioned"
|
||||
require "risc/padding"
|
||||
require "risc/positioned"
|
||||
require "vm"
|
||||
|
||||
require "parfait"
|
||||
require "register/machine"
|
||||
require "risc/machine"
|
||||
|
||||
class Fixnum
|
||||
def fits_u8?
|
||||
@ -19,6 +19,6 @@ class Fixnum
|
||||
end
|
||||
|
||||
|
||||
require "register/instruction"
|
||||
require "register/register_value"
|
||||
require "register/assembler"
|
||||
require "risc/instruction"
|
||||
require "risc/register_value"
|
||||
require "risc/assembler"
|
@ -1,7 +1,7 @@
|
||||
Register Machine
|
||||
Risc Machine
|
||||
================
|
||||
|
||||
The RegisterMachine, is an abstract machine with registers. Think of it as an arm machine with
|
||||
The RiscMachine, is an abstract machine with registers. Think of it as an arm machine with
|
||||
normal instruction names. It is not however an abstraction of existing hardware, but only
|
||||
of that subset that we need.
|
||||
|
||||
@ -20,13 +20,13 @@ express call semantics.
|
||||
Calls and syscalls
|
||||
------------------
|
||||
|
||||
The RegisterMachine only uses 1 fixed register, the currently worked on Message.
|
||||
The RiscMachine only uses 1 fixed register, the currently worked on Message.
|
||||
|
||||
There is no stack, rather messages form a linked list, and preparing to call, the data is pre-filled
|
||||
into the next message. Calling then means moving the new message to the current one and jumping
|
||||
to the address of the method. Returning is the somewhat reverse process.
|
||||
|
||||
Syscalls are implemented by *one* Syscall instruction. The Register machine does not specify/limit
|
||||
Syscalls are implemented by *one* Syscall instruction. The Risc machine does not specify/limit
|
||||
the meaning or number of syscalls. This is implemented by the level below, eg the arm/interpreter.
|
||||
|
||||
Interpreter
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
class LinkException < Exception
|
||||
end
|
||||
# Assemble the object machine into a binary.
|
||||
@ -49,7 +49,7 @@ module Register
|
||||
at += 8 # thats the padding
|
||||
# want to have the objects first in the executable
|
||||
@objects.each do | id , objekt|
|
||||
next if objekt.is_a? Register::Label # will get assembled as method.instructions
|
||||
next if objekt.is_a? Risc::Label # will get assembled as method.instructions
|
||||
next if objekt.is_a? Parfait::BinaryCode
|
||||
Positioned.set_position(objekt,at)
|
||||
at += objekt.padded_length
|
||||
@ -83,7 +83,7 @@ module Register
|
||||
def try_write_debug
|
||||
all = @objects.values.sort{|a,b| Positioned.position(a) <=> Positioned.position(b)}
|
||||
all.each do |objekt|
|
||||
next if objekt.is_a?(Register::Label)
|
||||
next if objekt.is_a?(Risc::Label)
|
||||
log.debug "Linked #{objekt.class}(#{objekt.object_id}) at #{Positioned.position(objekt)} / #{objekt.padded_length}"
|
||||
Positioned.position(objekt)
|
||||
end
|
||||
@ -106,7 +106,7 @@ module Register
|
||||
# then the objects , not code yet
|
||||
@objects.each do | id, objekt|
|
||||
next if objekt.is_a? Parfait::BinaryCode
|
||||
next if objekt.is_a? Register::Label # ignore
|
||||
next if objekt.is_a? Risc::Label # ignore
|
||||
write_any( objekt )
|
||||
end
|
||||
end
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# Booting is complicated, so it is extracted into this file, even it has only one entry point
|
||||
|
@ -1,5 +1,5 @@
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
module CompileHelper
|
||||
|
@ -1,5 +1,5 @@
|
||||
#integer related kernel functions
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
module Integer
|
||||
module ClassMethods
|
||||
@ -23,48 +23,48 @@ module Register
|
||||
q = compiler.process( Vm::Tree::KnownName.new( :self) )
|
||||
const = compiler.process( Vm::Tree::IntegerExpression.new(1) )
|
||||
# int tmp = self >> 1
|
||||
compiler.add_code Register.op( s , ">>" , tmp , const)
|
||||
compiler.add_code Risc.op( s , ">>" , tmp , const)
|
||||
# int q = self >> 2
|
||||
compiler.add_load_constant( s , 2 , const)
|
||||
compiler.add_code Register.op( s , ">>" , q , const)
|
||||
compiler.add_code Risc.op( s , ">>" , q , const)
|
||||
# q = q + tmp
|
||||
compiler.add_code Register.op( s , "+" , q , tmp )
|
||||
compiler.add_code Risc.op( s , "+" , q , tmp )
|
||||
# tmp = q >> 4
|
||||
compiler.add_load_constant( s , 4 , const)
|
||||
compiler.add_transfer( s, q , tmp)
|
||||
compiler.add_code Register.op( s , ">>" , tmp , const)
|
||||
compiler.add_code Risc.op( s , ">>" , tmp , const)
|
||||
# q = q + tmp
|
||||
compiler.add_code Register.op( s , "+" , q , tmp )
|
||||
compiler.add_code Risc.op( s , "+" , q , tmp )
|
||||
# tmp = q >> 8
|
||||
compiler.add_load_constant( s , 8 , const)
|
||||
compiler.add_transfer( s, q , tmp)
|
||||
compiler.add_code Register.op( s , ">>" , tmp , const)
|
||||
compiler.add_code Risc.op( s , ">>" , tmp , const)
|
||||
# q = q + tmp
|
||||
compiler.add_code Register.op( s , "+" , q , tmp )
|
||||
compiler.add_code Risc.op( s , "+" , q , tmp )
|
||||
# tmp = q >> 16
|
||||
compiler.add_load_constant( s , 16 , const)
|
||||
compiler.add_transfer( s, q , tmp)
|
||||
compiler.add_code Register.op( s , ">>" , tmp , const)
|
||||
compiler.add_code Risc.op( s , ">>" , tmp , const)
|
||||
# q = q + tmp
|
||||
compiler.add_code Register.op( s , "+" , q , tmp )
|
||||
compiler.add_code Risc.op( s , "+" , q , tmp )
|
||||
# q = q >> 3
|
||||
compiler.add_load_constant( s , 3 , const)
|
||||
compiler.add_code Register.op( s , ">>" , q , const)
|
||||
compiler.add_code Risc.op( s , ">>" , q , const)
|
||||
# tmp = q * 10
|
||||
compiler.add_load_constant( s , 10 , const)
|
||||
compiler.add_transfer( s, q , tmp)
|
||||
compiler.add_code Register.op( s , "*" , tmp , const)
|
||||
compiler.add_code Risc.op( s , "*" , tmp , const)
|
||||
# tmp = self - tmp
|
||||
compiler.add_code Register.op( s , "-" , me , tmp )
|
||||
compiler.add_code Risc.op( s , "-" , me , tmp )
|
||||
compiler.add_transfer( s , me , tmp)
|
||||
# tmp = tmp + 6
|
||||
compiler.add_load_constant( s , 6 , const)
|
||||
compiler.add_code Register.op( s , "+" , tmp , const )
|
||||
compiler.add_code Risc.op( s , "+" , tmp , const )
|
||||
# tmp = tmp >> 4
|
||||
compiler.add_load_constant( s , 4 , const)
|
||||
compiler.add_code Register.op( s , ">>" , tmp , const )
|
||||
compiler.add_code Risc.op( s , ">>" , tmp , const )
|
||||
# return q + tmp
|
||||
compiler.add_code Register.op( s , "+" , q , tmp )
|
||||
compiler.add_code Risc.op( s , "+" , q , tmp )
|
||||
compiler.add_reg_to_slot( s , q , :message , :return_value)
|
||||
return compiler.method
|
||||
end
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
module Kernel
|
||||
module ClassMethods
|
||||
@ -7,22 +7,22 @@ module Register
|
||||
# so it is responsible for initial setup
|
||||
def __init__ context
|
||||
compiler = Vm::MethodCompiler.create_method(:Kernel,:__init__ )
|
||||
new_start = Register.label("__init__ start" , "__init__" )
|
||||
new_start = Risc.label("__init__ start" , "__init__" )
|
||||
compiler.method.set_instructions( new_start)
|
||||
compiler.set_current new_start
|
||||
|
||||
space = Parfait.object_space
|
||||
space_reg = compiler.use_reg(:Space) #Set up the Space as self upon init
|
||||
compiler.add_load_constant("__init__ load Space", space , space_reg)
|
||||
message_ind = Register.resolve_to_index( :space , :first_message )
|
||||
message_ind = Risc.resolve_to_index( :space , :first_message )
|
||||
compiler.add_slot_to_reg( "__init__ load 1st message" , space_reg , message_ind , :message)
|
||||
compiler.add_reg_to_slot( "__init__ store Space in message", space_reg , :message , :receiver)
|
||||
#fixme: should add arg type here, as done in call_site (which this sort of is)
|
||||
exit_label = Register.label("_exit_label for __init__" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||
exit_label = Risc.label("_exit_label for __init__" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||
ret_tmp = compiler.use_reg(:Label)
|
||||
compiler.add_load_constant("__init__ load return", exit_label , ret_tmp)
|
||||
compiler.add_reg_to_slot("__init__ store return", ret_tmp , :message , :return_address)
|
||||
compiler.add_code Register.function_call( "__init__ issue call" , Parfait.object_space.get_main )
|
||||
compiler.add_code Risc.function_call( "__init__ issue call" , Parfait.object_space.get_main )
|
||||
compiler.add_code exit_label
|
||||
emit_syscall( compiler , :exit )
|
||||
return compiler.method
|
||||
@ -47,18 +47,18 @@ module Register
|
||||
# This relies on linux to save and restore all registers
|
||||
#
|
||||
def save_message(compiler)
|
||||
r8 = RegisterValue.new( :r8 , :Message)
|
||||
compiler.add_transfer("save_message", Register.message_reg , r8 )
|
||||
r8 = RiscValue.new( :r8 , :Message)
|
||||
compiler.add_transfer("save_message", Risc.message_reg , r8 )
|
||||
end
|
||||
|
||||
def restore_message(compiler)
|
||||
r8 = RegisterValue.new( :r8 , :Message)
|
||||
return_tmp = Register.tmp_reg :Integer
|
||||
r8 = RiscValue.new( :r8 , :Message)
|
||||
return_tmp = Risc.tmp_reg :Integer
|
||||
source = "_restore_message"
|
||||
# get the sys return out of the way
|
||||
compiler.add_transfer(source, Register.message_reg , return_tmp )
|
||||
# load the stored message into the base RegisterMachine
|
||||
compiler.add_transfer(source, r8 , Register.message_reg )
|
||||
compiler.add_transfer(source, Risc.message_reg , return_tmp )
|
||||
# load the stored message into the base RiscMachine
|
||||
compiler.add_transfer(source, r8 , Risc.message_reg )
|
||||
# save the return value into the message
|
||||
compiler.add_reg_to_slot( source , return_tmp , :message , :return_value )
|
||||
end
|
@ -1,6 +1,6 @@
|
||||
require_relative "compile_helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
class Object
|
||||
module ClassMethods
|
@ -1,6 +1,6 @@
|
||||
require "ast/sexp"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
class Space
|
||||
module ClassMethods
|
@ -1,6 +1,6 @@
|
||||
require_relative "compile_helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module Builtin
|
||||
module Word
|
||||
module ClassMethods
|
||||
@ -10,7 +10,7 @@ module Register
|
||||
compiler = Vm::MethodCompiler.create_method(:Word , :putstring ).init_method
|
||||
compiler.add_slot_to_reg( "putstring" , :message , :receiver , :new_message )
|
||||
index = Parfait::Word.get_length_index
|
||||
reg = RegisterValue.new(:r2 , :Integer)
|
||||
reg = RiscValue.new(:r2 , :Integer)
|
||||
compiler.add_slot_to_reg( "putstring" , :new_message , index , reg )
|
||||
Kernel.emit_syscall( compiler , :putstring )
|
||||
compiler.method
|
@ -1,11 +1,11 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# collect anything that is in the space but and reachable from init
|
||||
module Collector
|
||||
def self.collect_space
|
||||
@objects = {}
|
||||
keep Parfait.object_space , 0
|
||||
Register.machine.constants.each {|obj| keep(obj,0)}
|
||||
Risc.machine.constants.each {|obj| keep(obj,0)}
|
||||
@objects
|
||||
end
|
||||
|
||||
@ -13,7 +13,7 @@ module Register
|
||||
return if object.nil?
|
||||
return unless add_object( object , depth )
|
||||
# probably should make labels or even instructions derive from Parfait::Object, but . .
|
||||
if object.is_a? Register::Label
|
||||
if object.is_a? Risc::Label
|
||||
object.each_label { |l| self.add_object(l ,depth)}
|
||||
end
|
||||
return unless object.respond_to? :has_type?
|
||||
@ -38,7 +38,7 @@ module Register
|
||||
return true if objekt.is_a? Fixnum
|
||||
#puts message(objekt , depth)
|
||||
#puts "ADD #{objekt.inspect}, #{objekt.name}" if objekt.is_a? Parfait::TypedMethod
|
||||
unless objekt.is_a?( Parfait::Object) or objekt.is_a?( Symbol) or objekt.is_a?( Register::Label)
|
||||
unless objekt.is_a?( Parfait::Object) or objekt.is_a?( Symbol) or objekt.is_a?( Risc::Label)
|
||||
raise "adding non parfait #{objekt.class}"
|
||||
end
|
||||
#raise "Method #{objekt.name}" if objekt.is_a? Parfait::TypedMethod
|
@ -2,7 +2,7 @@
|
||||
# Events are stored in the `@events` ivar.
|
||||
module Eventable
|
||||
|
||||
# Register a handler for the given event name.
|
||||
# Risc a handler for the given event name.
|
||||
# The event name is the method name called on the handler object
|
||||
#
|
||||
# obj.on(:foo , some_object_that_implements foo( whateverargs)
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# the register machine has at least 8 registers, named r0-r5 , :lr and :pc (for historical reasons)
|
||||
# we can load and store their contents and
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
|
||||
# a branch must branch to a block.
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# ByteToReg moves a single byte into a register from memory.
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# name says it all really
|
||||
# only arg is the method object we want to call
|
||||
# assembly takes care of the rest (ie getting the address)
|
||||
@ -16,18 +16,18 @@ module Register
|
||||
end
|
||||
|
||||
def self.function_call( source , method )
|
||||
Register::FunctionCall.new( source , method )
|
||||
Risc::FunctionCall.new( source , method )
|
||||
end
|
||||
|
||||
def self.issue_call( compiler , callee )
|
||||
return_label = Register.label("_return_label #{callee.name}" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||
return_label = Risc.label("_return_label #{callee.name}" , "#{compiler.type.object_class.name}.#{compiler.method.name}" )
|
||||
ret_tmp = compiler.use_reg(:Label)
|
||||
compiler.add_load_constant("#{callee.name} load ret", return_label , ret_tmp)
|
||||
compiler.add_reg_to_slot("#{callee.name} store ret", ret_tmp , :new_message , :return_address)
|
||||
compiler.add_transfer("#{callee.name} move new message", Register.new_message_reg , Register.message_reg )
|
||||
compiler.add_code Register.function_call( "#{callee.name} call" , callee )
|
||||
compiler.add_transfer("#{callee.name} move new message", Risc.new_message_reg , Risc.message_reg )
|
||||
compiler.add_code Risc.function_call( "#{callee.name} call" , callee )
|
||||
compiler.add_code return_label
|
||||
compiler.add_transfer("#{callee.name} remove new message", Register.message_reg , Register.new_message_reg )
|
||||
compiler.add_transfer("#{callee.name} remove new message", Risc.message_reg , Risc.new_message_reg )
|
||||
compiler.add_slot_to_reg("#{callee.name} restore message" , :new_message , :caller , :message )
|
||||
end
|
||||
end
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# return from a function call
|
||||
# register and index specify where the return address is stored
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# Getter is a base class for get instructions (SlotToReg and ByteToReg , possibly more coming)
|
||||
#
|
||||
@ -7,7 +7,7 @@ module Register
|
||||
# Getter has a
|
||||
# - an array where the data comes from
|
||||
# - and (array) index
|
||||
# - Register that the data is moved to
|
||||
# - Risc that the data is moved to
|
||||
|
||||
# Getter and Setter api follow the pattern from -> to
|
||||
|
||||
@ -23,9 +23,9 @@ module Register
|
||||
@index = index
|
||||
@register = register
|
||||
raise "index 0 " if index == 0
|
||||
raise "Not integer or reg #{index}" unless index.is_a?(Numeric) or RegisterValue.look_like_reg(index)
|
||||
raise "Not register #{register}" unless RegisterValue.look_like_reg(register)
|
||||
raise "Not register #{array}" unless RegisterValue.look_like_reg(array)
|
||||
raise "Not integer or reg #{index}" unless index.is_a?(Numeric) or RiscValue.look_like_reg(index)
|
||||
raise "Not register #{register}" unless RiscValue.look_like_reg(register)
|
||||
raise "Not register #{array}" unless RiscValue.look_like_reg(array)
|
||||
end
|
||||
attr_accessor :array , :index , :register
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# A label is a placeholder for it's next Instruction
|
||||
# It's function is not to turn into code, but to be a valid brnch target
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# load a constant into a register
|
||||
#
|
||||
# first is the actual constant, either immediate register or object reference (from the space)
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
class OperatorInstruction < Instruction
|
||||
def initialize source , operator , left , right
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# RegToByte moves a byte into memory from a register.
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# RegToSlot moves data into memory from a register.
|
||||
# SlotToReg moves data into a register from memory.
|
||||
@ -7,7 +7,7 @@ module Register
|
||||
# This is because that is what cpu's can do. In programming terms this would be accessing
|
||||
# an element in an array, in the case of RegToSlot setting the register in the array.
|
||||
|
||||
# btw: to move data between registers, use RegisterTransfer
|
||||
# btw: to move data between registers, use RiscTransfer
|
||||
|
||||
class RegToSlot < Setter
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# transfer the constents of one register to another.
|
||||
# possibly called move in some cpus
|
||||
@ -10,7 +10,7 @@ module Register
|
||||
# Also it is used for moving temorary data
|
||||
#
|
||||
|
||||
class RegisterTransfer < Instruction
|
||||
class RiscTransfer < Instruction
|
||||
# initialize with from and to registers.
|
||||
# First argument from
|
||||
# second argument to
|
||||
@ -20,16 +20,16 @@ module Register
|
||||
super(source)
|
||||
@from = from
|
||||
@to = to
|
||||
raise "Fix me #{from}" unless from.is_a? RegisterValue
|
||||
raise "Fix me #{to}" unless to.is_a? RegisterValue
|
||||
raise "Fix me #{from}" unless from.is_a? RiscValue
|
||||
raise "Fix me #{to}" unless to.is_a? RiscValue
|
||||
end
|
||||
attr_reader :from, :to
|
||||
|
||||
def to_s
|
||||
"RegisterTransfer: #{from} -> #{to}"
|
||||
"RiscTransfer: #{from} -> #{to}"
|
||||
end
|
||||
end
|
||||
def self.transfer( source , from , to)
|
||||
RegisterTransfer.new( source , from , to)
|
||||
RiscTransfer.new( source , from , to)
|
||||
end
|
||||
end
|
@ -1,10 +1,10 @@
|
||||
module Register
|
||||
module Risc
|
||||
# Setter is a base class for set instructions (RegToSlot and RegToByte , possibly more coming)
|
||||
#
|
||||
# The instruction that is modelled is loading data from a register into an array
|
||||
#
|
||||
# Setter has a
|
||||
# - Register that the data is comes from
|
||||
# - Risc that the data is comes from
|
||||
# - an array where the data goes
|
||||
# - and (array) index
|
||||
|
||||
@ -21,9 +21,9 @@ module Register
|
||||
@array = array
|
||||
@index = index
|
||||
raise "index 0 " if index == 0
|
||||
raise "Not integer or reg #{index}" unless index.is_a?(Numeric) or RegisterValue.look_like_reg(index)
|
||||
raise "Not register #{register}" unless RegisterValue.look_like_reg(register)
|
||||
raise "Not register #{array}" unless RegisterValue.look_like_reg(array)
|
||||
raise "Not integer or reg #{index}" unless index.is_a?(Numeric) or RiscValue.look_like_reg(index)
|
||||
raise "Not register #{register}" unless RiscValue.look_like_reg(register)
|
||||
raise "Not register #{array}" unless RiscValue.look_like_reg(array)
|
||||
end
|
||||
attr_accessor :register , :array , :index
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# SlotToReg moves data into a register from memory.
|
||||
# RegToSlot moves data into memory from a register.
|
||||
@ -7,7 +7,7 @@ module Register
|
||||
# This is because that is what cpu's can do. In programming terms this would be accessing
|
||||
# an element in an array, in the case of SlotToReg setting the value in the array.
|
||||
|
||||
# btw: to move data between registers, use RegisterTransfer
|
||||
# btw: to move data between registers, use RiscTransfer
|
||||
|
||||
class SlotToReg < Getter
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# name says it all really
|
||||
# only arg is the method syscall name
|
@ -1,7 +1,7 @@
|
||||
|
||||
require_relative "eventable"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# An interpreter for the register level. As the register machine is a simple model,
|
||||
# interpreting it is not so terribly difficult.
|
||||
@ -62,8 +62,8 @@ module Register
|
||||
end
|
||||
|
||||
def get_register( reg )
|
||||
reg = reg.symbol if reg.is_a? Register::RegisterValue
|
||||
raise "Not a register #{reg}" unless Register::RegisterValue.look_like_reg(reg)
|
||||
reg = reg.symbol if reg.is_a? Risc::RiscValue
|
||||
raise "Not a register #{reg}" unless Risc::RiscValue.look_like_reg(reg)
|
||||
@registers[reg]
|
||||
end
|
||||
|
||||
@ -79,7 +79,7 @@ module Register
|
||||
@flags[:minus] = false
|
||||
end
|
||||
return if old === val
|
||||
reg = reg.symbol if reg.is_a? Register::RegisterValue
|
||||
reg = reg.symbol if reg.is_a? Risc::RiscValue
|
||||
@registers[reg] = val
|
||||
trigger(:register_changed, reg , old , val)
|
||||
end
|
||||
@ -184,7 +184,7 @@ module Register
|
||||
true
|
||||
end
|
||||
|
||||
def execute_RegisterTransfer
|
||||
def execute_RiscTransfer
|
||||
value = get_register @instruction.from
|
||||
set_register @instruction.to , value
|
||||
true
|
@ -1,7 +1,7 @@
|
||||
require_relative "collector"
|
||||
|
||||
module Register
|
||||
# The Register Machine is an abstraction of the register level. This is seperate from the
|
||||
module Risc
|
||||
# The Risc Machine is an abstraction of the register level. This is seperate from the
|
||||
# actual assembler level to allow for several cpu architectures.
|
||||
# The Instructions (see class Instruction) define what the machine can do (ie load/store/maths)
|
||||
|
@ -1,8 +1,8 @@
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
# RegisterValue is like a variable name, a storage location. The location is a register off course.
|
||||
# RiscValue is like a variable name, a storage location. The location is a register off course.
|
||||
|
||||
class RegisterValue
|
||||
class RiscValue
|
||||
|
||||
attr_accessor :symbol , :type , :value
|
||||
|
||||
@ -26,7 +26,7 @@ module Register
|
||||
end
|
||||
|
||||
def self.look_like_reg is_it
|
||||
return true if is_it.is_a? RegisterValue
|
||||
return true if is_it.is_a? RiscValue
|
||||
return false unless is_it.is_a? Symbol
|
||||
if( [:lr , :pc].include? is_it )
|
||||
return true
|
||||
@ -40,7 +40,7 @@ module Register
|
||||
|
||||
def == other
|
||||
return false if other.nil?
|
||||
return false if other.class != RegisterValue
|
||||
return false if other.class != RiscValue
|
||||
symbol == other.symbol
|
||||
end
|
||||
|
||||
@ -49,7 +49,7 @@ module Register
|
||||
int = @symbol[1,3].to_i
|
||||
raise "No more registers #{self}" if int > 12
|
||||
sym = "r#{int + 1}".to_sym
|
||||
RegisterValue.new( sym , type, value)
|
||||
RiscValue.new( sym , type, value)
|
||||
end
|
||||
|
||||
def sof_reference_name
|
||||
@ -63,19 +63,19 @@ module Register
|
||||
|
||||
# The register we use to store the current message object is :r0
|
||||
def self.message_reg
|
||||
RegisterValue.new :r0 , :Message
|
||||
RiscValue.new :r0 , :Message
|
||||
end
|
||||
|
||||
# The register we use to store the new message object is :r3
|
||||
# The new message is the one being built, to be sent
|
||||
def self.new_message_reg
|
||||
RegisterValue.new :r1 , :Message
|
||||
RiscValue.new :r1 , :Message
|
||||
end
|
||||
|
||||
# The first scratch register. There is a next_reg_use to get a next and next.
|
||||
# Current thinking is that scratch is schatch between instructions
|
||||
def self.tmp_reg( type , value = nil)
|
||||
RegisterValue.new :r2 , type , value
|
||||
RiscValue.new :r2 , type , value
|
||||
end
|
||||
|
||||
# The first arg is a class name (possibly lowercase) and the second an instance variable name.
|
||||
@ -96,9 +96,9 @@ module Register
|
||||
# These are mapped to register references.
|
||||
# The valid symbols (:message,:new_message) are the same that are returned
|
||||
# by the slots. All data (at any time) is in one of the instance variables of these two
|
||||
# objects. Register defines module methods with the same names (and _reg)
|
||||
# objects. Risc defines module methods with the same names (and _reg)
|
||||
def self.resolve_to_register( reference )
|
||||
return reference if reference.is_a?(RegisterValue)
|
||||
return reference if reference.is_a?(RiscValue)
|
||||
case reference
|
||||
when :message
|
||||
return message_reg
|
@ -9,8 +9,8 @@ AST::Node.class_eval do
|
||||
end
|
||||
|
||||
require "salama-object-file"
|
||||
require "register"
|
||||
require "register/builtin/space"
|
||||
require "risc"
|
||||
require "risc/builtin/space"
|
||||
require "arm/arm_machine"
|
||||
require "arm/translator"
|
||||
|
||||
|
@ -131,7 +131,7 @@ module Vm
|
||||
def init_method
|
||||
source = "_init_method"
|
||||
name = "#{method.for_type.name}.#{method.name}"
|
||||
@current = @method.set_instructions( Register.label(source, name))
|
||||
@current = @method.set_instructions( Risc.label(source, name))
|
||||
|
||||
# add the type of the locals to the existing NamedList instance
|
||||
locals_reg = use_reg(:Type , method.locals )
|
||||
@ -143,7 +143,7 @@ module Vm
|
||||
enter = @current # this is where method body goes
|
||||
add_label( source, "return #{name}")
|
||||
#load the return address into pc, affecting return. (other cpus have commands for this, but not arm)
|
||||
add_function_return( source , Register.message_reg , Register.resolve_to_index(:message , :return_address) )
|
||||
add_function_return( source , Risc.message_reg , Risc.resolve_to_index(:message , :return_address) )
|
||||
@current = enter
|
||||
self
|
||||
end
|
||||
@ -156,7 +156,7 @@ module Vm
|
||||
# add an instruction after the current (insertion point)
|
||||
# the added instruction will become the new insertion point
|
||||
def add_code instruction
|
||||
raise instruction.to_s unless instruction.is_a?(Register::Instruction)
|
||||
raise instruction.to_s unless instruction.is_a?(Risc::Instruction)
|
||||
raise instruction.to_s if( instruction.class.name.split("::").first == "Arm")
|
||||
@current.insert(instruction) #insert after current
|
||||
@current = instruction
|
||||
@ -166,7 +166,7 @@ module Vm
|
||||
[:label, :reg_to_slot , :slot_to_reg , :load_constant, :function_return ,
|
||||
:transfer , :reg_to_slot , :byte_to_reg , :reg_to_byte].each do |method|
|
||||
define_method("add_#{method}".to_sym) do |*args|
|
||||
add_code Register.send( method , *args )
|
||||
add_code Risc.send( method , *args )
|
||||
end
|
||||
end
|
||||
|
||||
@ -174,7 +174,7 @@ module Vm
|
||||
def use_reg( type , value = nil )
|
||||
raise "Not type #{type.inspect}" unless type.is_a?(Symbol) or type.is_a?(Parfait::Type)
|
||||
if @regs.empty?
|
||||
reg = Register.tmp_reg(type , value)
|
||||
reg = Risc.tmp_reg(type , value)
|
||||
else
|
||||
reg = @regs.last.next_reg_use(type , value)
|
||||
end
|
||||
|
@ -42,7 +42,7 @@ module Vm
|
||||
def assignment_value(statement)
|
||||
reset_regs # statements reset registers, ie have all at their disposal
|
||||
value = process(statement.value)
|
||||
raise "Not register #{v}" unless value.is_a?(Register::RegisterValue)
|
||||
raise "Not register #{v}" unless value.is_a?(Risc::RiscValue)
|
||||
value
|
||||
end
|
||||
# ensure the name given is not space and raise exception otherwise
|
||||
|
@ -5,7 +5,7 @@ module Vm
|
||||
|
||||
# Constant expressions can by definition be evaluated at compile time.
|
||||
# But that does not solve their storage, ie they need to be accessible at runtime from _somewhere_
|
||||
# So expressions move the data into a Register.
|
||||
# So expressions move the data into a Risc.
|
||||
# All expressions return registers
|
||||
|
||||
# But in the future (in the one that holds great things) we optimize those unneccesay moves away
|
||||
@ -38,7 +38,7 @@ module Vm
|
||||
def on_StringExpression expression
|
||||
value = Parfait.new_word expression.value.to_sym
|
||||
reg = use_reg :Word
|
||||
Register.machine.constants << value
|
||||
Risc.machine.constants << value
|
||||
add_load_constant( expression, value , reg )
|
||||
return reg
|
||||
end
|
||||
|
@ -19,7 +19,7 @@ module Vm
|
||||
set_arguments(method , statement.arguments)
|
||||
ret = use_reg( :Object ) #FIXME real return type
|
||||
|
||||
Register.issue_call( self , method )
|
||||
Risc.issue_call( self , method )
|
||||
|
||||
# the effect of the method is that the NewMessage Return slot will be filled, return it
|
||||
# but move it into a register too
|
||||
@ -30,7 +30,7 @@ module Vm
|
||||
private
|
||||
|
||||
def load_new_message(statement)
|
||||
new_message = Register.resolve_to_register(:new_message)
|
||||
new_message = Risc.resolve_to_register(:new_message)
|
||||
add_slot_to_reg(statement, :message , :next_message , new_message )
|
||||
new_message
|
||||
end
|
||||
@ -87,7 +87,7 @@ module Vm
|
||||
reset_regs
|
||||
i = i + 1 # disregarding type field
|
||||
val = process( arg) # processing should return the register with the value
|
||||
raise "Not register #{val}" unless val.is_a?(Register::RegisterValue)
|
||||
raise "Not register #{val}" unless val.is_a?(Risc::RiscValue)
|
||||
#FIXME definately needs some tests
|
||||
raise "TypeMismatch calling with #{val.type} , instead of #{arg_type.type_at(i)}" if val.type != arg_type.type_at(i)
|
||||
list_reg = use_reg(:NamedList , arguments )
|
||||
|
@ -20,8 +20,8 @@ module Vm
|
||||
def compile_if_condition( statement )
|
||||
reset_regs
|
||||
process(statement.condition)
|
||||
branch_class = Object.const_get "Register::Is#{statement.branch_type.capitalize}"
|
||||
true_block = Register.label(statement, "if_true")
|
||||
branch_class = Object.const_get "Risc::Is#{statement.branch_type.capitalize}"
|
||||
true_block = Risc.label(statement, "if_true")
|
||||
add_code branch_class.new( statement.condition , true_block )
|
||||
return true_block
|
||||
end
|
||||
@ -33,8 +33,8 @@ module Vm
|
||||
def compile_if_false( statement )
|
||||
reset_regs
|
||||
process(statement.if_false) if statement.if_false.statements
|
||||
merge = Register.label(statement , "if_merge")
|
||||
add_code Register::Branch.new(statement.if_false, merge )
|
||||
merge = Risc.label(statement , "if_merge")
|
||||
add_code Risc::Branch.new(statement.if_false, merge )
|
||||
merge
|
||||
end
|
||||
end
|
||||
|
@ -51,7 +51,7 @@ module Vm
|
||||
|
||||
def load_special_message(statement)
|
||||
reg = use_reg :Message
|
||||
add_transfer( "#{statement} load message", Register.message_reg , reg )
|
||||
add_transfer( "#{statement} load message", Risc.message_reg , reg )
|
||||
return reg
|
||||
end
|
||||
end #module
|
||||
|
@ -6,9 +6,9 @@ module Vm
|
||||
# left and right must be expressions. Expressions return a register when compiled
|
||||
left_reg = process(statement.left_expression)
|
||||
right_reg = process(statement.right_expression)
|
||||
raise "Not register #{left_reg}" unless left_reg.is_a?(Register::RegisterValue)
|
||||
raise "Not register #{right_reg}" unless right_reg.is_a?(Register::RegisterValue)
|
||||
add_code Register::OperatorInstruction.new(statement,statement.operator,left_reg,right_reg)
|
||||
raise "Not register #{left_reg}" unless left_reg.is_a?(Risc::RiscValue)
|
||||
raise "Not register #{right_reg}" unless right_reg.is_a?(Risc::RiscValue)
|
||||
add_code Risc::OperatorInstruction.new(statement,statement.operator,left_reg,right_reg)
|
||||
return left_reg # though this has wrong value attached
|
||||
end
|
||||
end
|
||||
|
@ -13,7 +13,7 @@ module Vm
|
||||
|
||||
compile_while_condition( statement )
|
||||
|
||||
branch_class = Object.const_get "Register::Is#{statement.branch_type.capitalize}"
|
||||
branch_class = Object.const_get "Risc::Is#{statement.branch_type.capitalize}"
|
||||
# this is where the while ends and both branches meet
|
||||
add_code branch_class.new( statement.condition , start )
|
||||
|
||||
@ -22,13 +22,13 @@ module Vm
|
||||
private
|
||||
|
||||
def compile_while_preamble( statement )
|
||||
condition_label = Register.label(statement.condition , "condition_label")
|
||||
condition_label = Risc.label(statement.condition , "condition_label")
|
||||
# unconditionally branch to the condition upon entering the loop
|
||||
add_code Register::Branch.new(statement.condition , condition_label)
|
||||
add_code Risc::Branch.new(statement.condition , condition_label)
|
||||
condition_label
|
||||
end
|
||||
def compile_while_body( statement )
|
||||
start = Register.label(statement , "while_start" )
|
||||
start = Risc.label(statement , "while_start" )
|
||||
add_code start
|
||||
reset_regs
|
||||
process(statement.statements)
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# So when an object calls a method, or sends a message, this is what it sends: a Message
|
||||
|
||||
# A message contains the sender, return and exceptional return addresses,the arguments,
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# Passes, or BlockPasses, could have been procs that just get each block passed.
|
||||
# Instead they are proper objects in case they want to save state.
|
||||
# The idea is
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# Plock (Proc-Block) is mostly a Block but also somewhat Proc-ish: A Block that carries data.
|
||||
#
|
||||
# Data in a Block is usefull in the same way data in objects is. Plocks being otherwise just code.
|
||||
@ -23,18 +23,18 @@ module Register
|
||||
def initialize(name , method , next_block )
|
||||
super
|
||||
@data = []
|
||||
@branch_code = RegisterMachine.instance.b next_block
|
||||
@branch_code = RiscMachine.instance.b next_block
|
||||
end
|
||||
|
||||
def set_next next_b
|
||||
super
|
||||
@branch_code = RegisterMachine.instance.b next_block
|
||||
@branch_code = RiscMachine.instance.b next_block
|
||||
end
|
||||
|
||||
# Data gets assembled after methods
|
||||
def add_data o
|
||||
return if @objects.include? o
|
||||
raise "must be derived from Code #{o.inspect}" unless o.is_a? Register::Code
|
||||
raise "must be derived from Code #{o.inspect}" unless o.is_a? Risc::Code
|
||||
@data << o # TODO check type , no basic values allowed (must be wrapped)
|
||||
end
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
module Register
|
||||
module Risc
|
||||
# A slot is a slot in an object. It is the storage location for a value.
|
||||
# (Remember, values are typed)
|
||||
# From a memory perspective a slot is an index into an array (the object)
|
||||
|
@ -10,7 +10,7 @@ module Fragments
|
||||
# define setup to NOT load parfait.
|
||||
def setup
|
||||
@stdout = ""
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
end
|
||||
|
||||
def main()
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative 'helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestBasicClass < MiniTest::Test
|
||||
include Fragments
|
||||
|
||||
|
@ -21,7 +21,7 @@ module RuntimeTests
|
||||
end
|
||||
|
||||
def load_program
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
@machine.parse_and_compile main()
|
||||
@machine.collect
|
||||
end
|
||||
@ -34,7 +34,7 @@ module RuntimeTests
|
||||
|
||||
def check_local ret = nil
|
||||
load_program
|
||||
interpreter = Register::Interpreter.new
|
||||
interpreter = Risc::Interpreter.new
|
||||
interpreter.start @machine.init
|
||||
count = 0
|
||||
begin
|
||||
@ -89,7 +89,7 @@ module RuntimeTests
|
||||
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
|
||||
Risc.machine.translate_arm
|
||||
writer = Elf::ObjectWriter.new
|
||||
writer.save file_name
|
||||
file_name
|
||||
|
@ -11,7 +11,7 @@ module ParfaitTests
|
||||
|
||||
def setup
|
||||
@stdout = ""
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
Vm::Compiler.load_parfait
|
||||
end
|
||||
|
||||
|
@ -20,7 +20,7 @@ class TestRunner < MiniTest::Test
|
||||
def execute file
|
||||
string = File.read(file)
|
||||
parser = Parser::RubyX.new
|
||||
object_space = Register::Program.new "Arm"
|
||||
object_space = Risc::Program.new "Arm"
|
||||
#TODO : files would have to include s-expressions now
|
||||
syntax = parser.parse_with_debug(string, reporter: Parslet::ErrorReporter::Deepest.new)
|
||||
assert syntax
|
||||
@ -32,7 +32,7 @@ class TestRunner < MiniTest::Test
|
||||
expr = part.compile( program.context )
|
||||
else
|
||||
expr = part.compile( program.context )
|
||||
raise "should be function definition for now" unless expr.is_a? Register::Function
|
||||
raise "should be function definition for now" unless expr.is_a? Risc::Function
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -82,7 +82,7 @@ module Arm
|
||||
end
|
||||
|
||||
def label pos = 0x22
|
||||
l = Register.label("some" , "Label")
|
||||
l = Risc.label("some" , "Label")
|
||||
l.set_position pos
|
||||
l
|
||||
end
|
||||
|
@ -25,7 +25,7 @@ module Arm
|
||||
code.set_position(0)
|
||||
begin # mov 512(0x200) = e3 a0 0c 02 add 34(0x22) = e2 90 00 22
|
||||
assert_code code , :mov , [ 0x02,0x0c,0xb0,0xe3 , 0x22,0x00,0x90,0xe2]
|
||||
rescue Register::LinkException
|
||||
rescue Risc::LinkException
|
||||
retry
|
||||
end
|
||||
end
|
||||
@ -35,28 +35,28 @@ module Arm
|
||||
end
|
||||
|
||||
def test_shiftr1
|
||||
code = @machine.mov :r1, :r2 , :shift_asr => Register::RegisterValue.new(:r3 , :Integer)
|
||||
code = @machine.mov :r1, :r2 , :shift_asr => Risc::RiscValue.new(:r3 , :Integer)
|
||||
assert_code code , :mov , [0x52,0x13,0xb0,0xe1] #e1 b0 13 52
|
||||
end
|
||||
def test_shiftr2
|
||||
code = @machine.mov :r2, :r3 , :shift_asr => Register::RegisterValue.new(:r4 , :Integer)
|
||||
code = @machine.mov :r2, :r3 , :shift_asr => Risc::RiscValue.new(:r4 , :Integer)
|
||||
assert_code code , :mov , [0x53,0x24,0xb0,0xe1] #e1 b0 24 53
|
||||
end
|
||||
def test_shiftr3
|
||||
code = @machine.mov :r3, :r4 , :shift_asr => Register::RegisterValue.new(:r5 , :Integer)
|
||||
code = @machine.mov :r3, :r4 , :shift_asr => Risc::RiscValue.new(:r5 , :Integer)
|
||||
assert_code code , :mov , [0x54,0x35,0xb0,0xe1] #e1 b0 35 54
|
||||
end
|
||||
|
||||
def test_shiftl1
|
||||
code = @machine.mov :r1, :r2 , :shift_lsr => Register::RegisterValue.new(:r3 , :Integer)
|
||||
code = @machine.mov :r1, :r2 , :shift_lsr => Risc::RiscValue.new(:r3 , :Integer)
|
||||
assert_code code , :mov , [0x32,0x13,0xb0,0xe1] #e1 b0 13 32
|
||||
end
|
||||
def test_shiftl2
|
||||
code = @machine.mov :r2, :r3 , :shift_lsr => Register::RegisterValue.new(:r4 , :Integer)
|
||||
code = @machine.mov :r2, :r3 , :shift_lsr => Risc::RiscValue.new(:r4 , :Integer)
|
||||
assert_code code , :mov , [0x33,0x24,0xb0,0xe1] #e1 b0 24 33
|
||||
end
|
||||
def test_shiftl3
|
||||
code = @machine.mov :r3, :r4 , :shift_lsr => Register::RegisterValue.new(:r5 , :Integer)
|
||||
code = @machine.mov :r3, :r4 , :shift_lsr => Risc::RiscValue.new(:r5 , :Integer)
|
||||
assert_code code , :mov , [0x34,0x35,0xb0,0xe1] #e1 b0 35 34
|
||||
end
|
||||
|
||||
|
@ -8,7 +8,7 @@ module BenchTests
|
||||
|
||||
def setup
|
||||
@stdout = ""
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
# Vm::Compiler.load_parfait
|
||||
# most interesting parts saved as interger/word .soml in this dir
|
||||
end
|
||||
|
@ -4,9 +4,9 @@ class HelloTest < MiniTest::Test
|
||||
include AST::Sexp
|
||||
|
||||
def check
|
||||
machine = Register.machine.boot
|
||||
machine = Risc.machine.boot
|
||||
Vm.compile_ast( @input )
|
||||
objects = Register::Collector.collect_space
|
||||
objects = Risc::Collector.collect_space
|
||||
machine.translate_arm
|
||||
writer = Elf::ObjectWriter.new(machine , objects )
|
||||
writer.save "test/hello.o"
|
||||
|
@ -3,14 +3,14 @@ require_relative "../helper"
|
||||
class TestZeroCode < MiniTest::Test
|
||||
|
||||
def setup
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@space.each_type do | type |
|
||||
type.method_names.each do |method|
|
||||
type.remove_method(method) unless keeper(method)
|
||||
end
|
||||
end
|
||||
@objects = Register::Collector.collect_space
|
||||
@objects = Risc::Collector.collect_space
|
||||
end
|
||||
def keeper name
|
||||
name == :main or name == :__init__
|
||||
|
@ -28,7 +28,7 @@ module Compiling
|
||||
|
||||
end
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
# relies on @interpreter instance to be set up during setup
|
||||
module InterpreterHelpers
|
||||
|
||||
@ -68,7 +68,7 @@ module Register
|
||||
puts e
|
||||
puts e.backtrace
|
||||
end
|
||||
str = classes.to_s.gsub("Register::","")
|
||||
str = classes.to_s.gsub("Risc::","")
|
||||
str.split(",").each_slice(5).each do |line|
|
||||
puts " " + line.join(",") + ","
|
||||
end
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestAttributes < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@mess = @space.first_message
|
||||
@type = @mess.get_type
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestClass < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@try = @space.create_class :Try , :Object
|
||||
end
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestMessage < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@mess = @space.first_message
|
||||
end
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestNamedLists < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@named_list = @space.first_message.locals
|
||||
@type = @named_list.get_type
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestSpace < MiniTest::Test
|
||||
|
||||
def setup
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
end
|
||||
|
||||
|
@ -3,7 +3,7 @@ module Parfait
|
||||
class TestEmptyWord < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@word = Parfait::Word.new(0)
|
||||
end
|
||||
def test_word_create
|
||||
@ -29,7 +29,7 @@ end
|
||||
class TestWord < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@word = Parfait::Word.new(5)
|
||||
end
|
||||
def test_len
|
||||
|
@ -1,2 +0,0 @@
|
||||
require_relative "../helper"
|
||||
Register.machine.boot unless Register.machine.booted
|
2
test/risc/helper.rb
Normal file
2
test/risc/helper.rb
Normal file
@ -0,0 +1,2 @@
|
||||
require_relative "../helper"
|
||||
Risc.machine.boot unless Risc.machine.booted
|
@ -1,18 +1,18 @@
|
||||
require_relative "../helper"
|
||||
require "register/interpreter"
|
||||
require "risc/interpreter"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module Ticker
|
||||
include AST::Sexp
|
||||
include InterpreterHelpers
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
do_clean_compile
|
||||
Vm.compile_ast( @input )
|
||||
Collector.collect_space
|
||||
@interpreter = Interpreter.new
|
||||
@interpreter.start Register.machine.init
|
||||
@interpreter.start Risc.machine.init
|
||||
end
|
||||
|
||||
# must be after boot, but before main compile, to define method
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class AddTest < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -21,7 +21,7 @@ HERE
|
||||
check_chain [Branch, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
LoadConstant, OperatorInstruction, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
end
|
||||
|
||||
@ -32,7 +32,7 @@ HERE
|
||||
end
|
||||
def test_transfer
|
||||
transfer = ticks 19
|
||||
assert_equal RegisterTransfer , transfer.class
|
||||
assert_equal RiscTransfer , transfer.class
|
||||
assert_equal @interpreter.get_register(transfer.to) , @interpreter.get_register(transfer.from)
|
||||
end
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestInterpretRegToByte < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -26,11 +26,11 @@ HERE
|
||||
LoadConstant, RegToSlot, LoadConstant, RegToSlot, LoadConstant,
|
||||
SlotToReg, RegToSlot, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot,
|
||||
RegisterTransfer, FunctionCall, Label, LoadConstant, SlotToReg,
|
||||
RiscTransfer, FunctionCall, Label, LoadConstant, SlotToReg,
|
||||
RegToSlot, SlotToReg, SlotToReg, SlotToReg, SlotToReg,
|
||||
SlotToReg, RegToByte, Label, FunctionReturn, RegisterTransfer,
|
||||
SlotToReg, RegToByte, Label, FunctionReturn, RiscTransfer,
|
||||
SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot,
|
||||
Label, FunctionReturn, RegisterTransfer, Syscall, NilClass]
|
||||
Label, FunctionReturn, RiscTransfer, Syscall, NilClass]
|
||||
end
|
||||
|
||||
def test_branch
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class IfCalledTest < MiniTest::Test
|
||||
include Ticker
|
||||
include Compiling
|
||||
@ -38,17 +38,17 @@ HERE
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, SlotToReg,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, LoadConstant,
|
||||
SlotToReg, RegToSlot, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label,
|
||||
LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label,
|
||||
LoadConstant, SlotToReg, RegToSlot, SlotToReg, SlotToReg,
|
||||
LoadConstant, OperatorInstruction, IsZero, SlotToReg, LoadConstant,
|
||||
RegToSlot, LoadConstant, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall,
|
||||
RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall,
|
||||
Label, LoadConstant, SlotToReg, RegToSlot, SlotToReg,
|
||||
SlotToReg, RegisterTransfer, Syscall, RegisterTransfer, RegisterTransfer,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, SlotToReg,
|
||||
SlotToReg, RiscTransfer, Syscall, RiscTransfer, RiscTransfer,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, SlotToReg,
|
||||
SlotToReg, Branch, Label, Label, FunctionReturn,
|
||||
RegisterTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RiscTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
end
|
||||
end
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class AddChange < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -40,7 +40,7 @@ module Register
|
||||
check_chain [Branch, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
LoadConstant, OperatorInstruction, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
end
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class MultTest < MiniTest::Test
|
||||
include Ticker
|
||||
include AST::Sexp
|
||||
@ -22,7 +22,7 @@ HERE
|
||||
check_chain [Branch, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
LoadConstant, OperatorInstruction, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
check_return 0
|
||||
end
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class PlusTest < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -21,7 +21,7 @@ HERE
|
||||
check_chain [Branch, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
LoadConstant, OperatorInstruction, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
check_return 0
|
||||
end
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestPuts < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -21,12 +21,12 @@ HERE
|
||||
check_chain [Branch, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, SlotToReg,
|
||||
LoadConstant, RegToSlot, LoadConstant, RegToSlot, LoadConstant,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer,
|
||||
FunctionCall, Label, LoadConstant, SlotToReg, RegToSlot,
|
||||
SlotToReg, SlotToReg, RegisterTransfer, Syscall, RegisterTransfer,
|
||||
RegisterTransfer, RegToSlot, Label, FunctionReturn, RegisterTransfer,
|
||||
SlotToReg, SlotToReg, RiscTransfer, Syscall, RiscTransfer,
|
||||
RiscTransfer, RegToSlot, Label, FunctionReturn, RiscTransfer,
|
||||
SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot,
|
||||
Label, FunctionReturn, RegisterTransfer, Syscall, NilClass]
|
||||
Label, FunctionReturn, RiscTransfer, Syscall, NilClass]
|
||||
end
|
||||
|
||||
def test_branch
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestInterpretByteToReg < MiniTest::Test
|
||||
include Ticker
|
||||
|
||||
@ -25,11 +25,11 @@ HERE
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, SlotToReg,
|
||||
LoadConstant, RegToSlot, LoadConstant, RegToSlot, LoadConstant,
|
||||
SlotToReg, RegToSlot, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label,
|
||||
LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label,
|
||||
LoadConstant, SlotToReg, RegToSlot, SlotToReg, SlotToReg,
|
||||
SlotToReg, ByteToReg, RegToSlot, Label, FunctionReturn,
|
||||
RegisterTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RiscTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
end
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class IfSimpleTest < MiniTest::Test
|
||||
include Ticker
|
||||
include Compiling
|
||||
@ -30,12 +30,12 @@ HERE
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
LoadConstant, OperatorInstruction, IsZero, SlotToReg, LoadConstant,
|
||||
RegToSlot, LoadConstant, RegToSlot, LoadConstant, SlotToReg,
|
||||
RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall,
|
||||
RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall,
|
||||
Label, LoadConstant, SlotToReg, RegToSlot, SlotToReg,
|
||||
SlotToReg, RegisterTransfer, Syscall, RegisterTransfer, RegisterTransfer,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, SlotToReg,
|
||||
SlotToReg, RiscTransfer, Syscall, RiscTransfer, RiscTransfer,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, SlotToReg,
|
||||
SlotToReg, Branch, Label, LoadConstant, SlotToReg,
|
||||
RegToSlot, Label, FunctionReturn, RegisterTransfer, Syscall,
|
||||
RegToSlot, Label, FunctionReturn, RiscTransfer, Syscall,
|
||||
NilClass]
|
||||
end
|
||||
end
|
@ -1,10 +1,10 @@
|
||||
require_relative "../helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestAssembler < MiniTest::Test
|
||||
|
||||
def setup
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
end
|
||||
def test_no_object
|
||||
@assembler = Assembler.new(@machine , {})
|
@ -1,10 +1,10 @@
|
||||
require_relative "../helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestCollector < MiniTest::Test
|
||||
def test_simple_collect
|
||||
Machine.new.boot
|
||||
objects = Register::Collector.collect_space
|
||||
objects = Risc::Collector.collect_space
|
||||
assert ((350 < objects.length) or (430 > objects.length)) , objects.length.to_s
|
||||
end
|
||||
end
|
@ -4,7 +4,7 @@ require_relative "../helper"
|
||||
class TestCompat < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
end
|
||||
|
||||
def test_list_create_from_array
|
@ -1,6 +1,6 @@
|
||||
require_relative "../helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestInstructions < MiniTest::Test
|
||||
def setup
|
||||
@label = Label.new("test" , "test")
|
@ -1,14 +1,14 @@
|
||||
require_relative "../helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestMachine < MiniTest::Test
|
||||
|
||||
def setup
|
||||
@machine = Register.machine.boot
|
||||
@machine = Risc.machine.boot
|
||||
end
|
||||
|
||||
def test_collect_all_types
|
||||
objects = Register::Collector.collect_space
|
||||
objects = Risc::Collector.collect_space
|
||||
objects.each do |id, objekt|
|
||||
next unless objekt.is_a?( Parfait::Type )
|
||||
assert Parfait.object_space.get_type_for( objekt.hash ) , objekt.hash
|
@ -2,7 +2,7 @@ require_relative "../helper"
|
||||
|
||||
class TestPositioned < MiniTest::Test
|
||||
def setup
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
end
|
||||
def test_list1
|
||||
list = Parfait.new_list([1])
|
@ -3,6 +3,8 @@ require "register/interpreter"
|
||||
require "parser/ruby22"
|
||||
require "yaml"
|
||||
|
||||
# An experiment to find out how much ruby there is to achieve bootstrap
|
||||
#
|
||||
class Walker < AST::Processor
|
||||
def initialize collector
|
||||
@collector = collector
|
||||
|
@ -1,12 +1,12 @@
|
||||
require_relative '../helper'
|
||||
require "register/interpreter"
|
||||
require "risc/interpreter"
|
||||
require "parser/ruby22"
|
||||
|
||||
module Rubyx
|
||||
module RubyxTests
|
||||
include CompilerHelper
|
||||
include Register::InterpreterHelpers
|
||||
subs = ObjectSpace.each_object(Class).select { |klass| klass < Register::Instruction }
|
||||
include Risc::InterpreterHelpers
|
||||
subs = ObjectSpace.each_object(Class).select { |klass| klass < Risc::Instruction }
|
||||
subs.each do |clazz|
|
||||
name = clazz.to_s
|
||||
next if name.include?("Arm")
|
||||
|
@ -3,17 +3,17 @@ require_relative 'helper'
|
||||
module Rubyx
|
||||
class TestRubyHello < MiniTest::Test
|
||||
include RubyxTests
|
||||
Branch = Register::Branch
|
||||
Label = Register::Label
|
||||
Branch = Risc::Branch
|
||||
Label = Risc::Label
|
||||
|
||||
def setup
|
||||
@string_input = as_main '"Hello there".putstring'
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
# do_clean_compile
|
||||
RubyCompiler.compile @string_input
|
||||
Register::Collector.collect_space
|
||||
@interpreter = Register::Interpreter.new
|
||||
@interpreter.start Register.machine.init
|
||||
Risc::Collector.collect_space
|
||||
@interpreter = Risc::Interpreter.new
|
||||
@interpreter.start Risc.machine.init
|
||||
end
|
||||
|
||||
def test_chain
|
||||
@ -22,16 +22,16 @@ module Rubyx
|
||||
LoadConstant, RegToSlot, FunctionCall, Label, LoadConstant,
|
||||
SlotToReg, RegToSlot, SlotToReg, LoadConstant, RegToSlot,
|
||||
LoadConstant, RegToSlot, LoadConstant, SlotToReg, RegToSlot,
|
||||
LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label,
|
||||
LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label,
|
||||
LoadConstant, SlotToReg, RegToSlot, SlotToReg, SlotToReg,
|
||||
RegisterTransfer, Syscall, RegisterTransfer, RegisterTransfer, RegToSlot,
|
||||
Label, FunctionReturn, RegisterTransfer, SlotToReg, SlotToReg,
|
||||
Label, FunctionReturn, RegisterTransfer, Syscall, NilClass]
|
||||
RiscTransfer, Syscall, RiscTransfer, RiscTransfer, RegToSlot,
|
||||
Label, FunctionReturn, RiscTransfer, SlotToReg, SlotToReg,
|
||||
Label, FunctionReturn, RiscTransfer, Syscall, NilClass]
|
||||
end
|
||||
|
||||
def test_overflow
|
||||
instruction = ticks( 24 )
|
||||
assert_equal Register::FunctionCall , instruction.class
|
||||
assert_equal Risc::FunctionCall , instruction.class
|
||||
assert_equal :putstring , instruction.method.name
|
||||
end
|
||||
|
||||
|
@ -5,7 +5,7 @@ module Rubyx
|
||||
class TestLocalsCollector < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
end
|
||||
|
||||
def parse_collect( input )
|
||||
|
@ -5,7 +5,7 @@ module Rubyx
|
||||
class TestMethodCollector < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
end
|
||||
|
||||
def parse_collect( input )
|
||||
|
@ -5,7 +5,7 @@ module Rubyx
|
||||
class TestNormalizer < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
end
|
||||
|
||||
def test_no_thing
|
||||
|
@ -5,7 +5,7 @@ module Rubyx
|
||||
class TestTypeCollector < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
end
|
||||
|
||||
def parse_collect( input )
|
||||
|
@ -4,7 +4,7 @@ module Rubyx
|
||||
class TestCompiler < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
end
|
||||
|
||||
def test_doesnt_create_existing_clas
|
||||
|
@ -5,7 +5,7 @@ module Rubyx
|
||||
include CompilerHelper
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
end
|
||||
|
||||
def create_method
|
||||
|
@ -8,6 +8,6 @@ require_relative "rubyx/test_all"
|
||||
|
||||
require_relative "parfait/test_all"
|
||||
|
||||
require_relative "register/test_all"
|
||||
require_relative "risc/test_all"
|
||||
|
||||
require_relative "vm/test_all"
|
||||
|
@ -1,3 +1,3 @@
|
||||
require_relative "../helper"
|
||||
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative '../helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
module SpaceHack
|
||||
# test hack to in place change object type
|
||||
def add_space_field(name,type)
|
||||
@ -12,7 +12,7 @@ module Register
|
||||
include SpaceHack
|
||||
|
||||
def check
|
||||
Register.machine.boot unless Register.machine.booted
|
||||
Risc.machine.boot unless Risc.machine.booted
|
||||
compiler = Vm::MethodCompiler.new Parfait.object_space.get_main
|
||||
code = Vm.ast_to_code @input
|
||||
assert code.to_s , @input
|
||||
@ -30,7 +30,7 @@ module Register
|
||||
include SpaceHack
|
||||
|
||||
def setup
|
||||
Register.machine.boot # force boot to reset main
|
||||
Risc.machine.boot # force boot to reset main
|
||||
end
|
||||
|
||||
def preamble
|
||||
@ -71,7 +71,7 @@ module Register
|
||||
def should( all )
|
||||
#preamble.each {all.shift}
|
||||
#postamble.each {all.pop}
|
||||
str = all.to_s.gsub("Register::","")
|
||||
str = all.to_s.gsub("Risc::","")
|
||||
ret = ""
|
||||
str.split(",").each_slice(6).each do |line|
|
||||
ret += " " + line.join(",") + " ,\n"
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative 'helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestAssignStatement < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
@ -44,8 +44,8 @@ module Register
|
||||
Parfait.object_space.get_main.add_local(:r , :Object)
|
||||
@input = s(:statements, s(:l_assignment, s(:local, :r), s(:call, :main, s(:arguments))))
|
||||
@expect = [Label, SlotToReg, SlotToReg, RegToSlot, LoadConstant, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer ,
|
||||
FunctionCall, Label, RegisterTransfer, SlotToReg, SlotToReg, SlotToReg ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer ,
|
||||
FunctionCall, Label, RiscTransfer, SlotToReg, SlotToReg, SlotToReg ,
|
||||
RegToSlot, LoadConstant, SlotToReg, RegToSlot, Label, FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
|
@ -1,14 +1,14 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
|
||||
class TestBasic < MiniTest::Test
|
||||
include ExpressionHelper
|
||||
include AST::Sexp
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
@output = Register::RegisterValue
|
||||
Risc.machine.boot
|
||||
@output = Risc::RiscValue
|
||||
end
|
||||
|
||||
def test_number
|
||||
|
@ -1,13 +1,13 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestCall < MiniTest::Test
|
||||
include ExpressionHelper
|
||||
include AST::Sexp
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
@output = Register::RegisterValue
|
||||
Risc.machine.boot
|
||||
@output = Risc::RiscValue
|
||||
end
|
||||
|
||||
def test_call_main_plain
|
||||
|
@ -1,7 +1,7 @@
|
||||
require_relative 'helper'
|
||||
require_relative "test_call_expression"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestCallStatement < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
@ -9,8 +9,8 @@ module Register
|
||||
clean_compile :Integer, :puti, {}, s(:statements, s(:return, s(:int, 1)))
|
||||
@input = s(:call, :puti , s(:arguments), s(:receiver, s(:int, 42)))
|
||||
@expect = [Label, SlotToReg, LoadConstant, RegToSlot, LoadConstant, RegToSlot, LoadConstant ,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label ,
|
||||
RegisterTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label ,
|
||||
RiscTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
@ -21,8 +21,8 @@ module Register
|
||||
|
||||
@input =s(:call, :putstr, s(:arguments), s(:receiver, s(:string, "Hello")))
|
||||
@expect = [Label, SlotToReg, LoadConstant, RegToSlot, LoadConstant, RegToSlot, LoadConstant ,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label ,
|
||||
RegisterTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label ,
|
||||
RiscTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
@ -34,7 +34,7 @@ module Register
|
||||
|
||||
@expect = [Label, LoadConstant, SlotToReg, RegToSlot, SlotToReg, SlotToReg, SlotToReg ,
|
||||
RegToSlot, LoadConstant, RegToSlot, LoadConstant, SlotToReg, RegToSlot, LoadConstant ,
|
||||
RegToSlot, RegisterTransfer, FunctionCall, Label, RegisterTransfer, SlotToReg, SlotToReg ,
|
||||
RegToSlot, RiscTransfer, FunctionCall, Label, RiscTransfer, SlotToReg, SlotToReg ,
|
||||
LoadConstant, SlotToReg, RegToSlot, Label, FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
@ -45,8 +45,8 @@ module Register
|
||||
|
||||
@input =s(:statements, s(:call, :add, s(:arguments), s(:receiver, s(:local, :test_l))))
|
||||
@expect = [Label, SlotToReg, SlotToReg, SlotToReg, RegToSlot, LoadConstant, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall ,
|
||||
Label, RegisterTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall ,
|
||||
Label, RiscTransfer, SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot ,
|
||||
Label, FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
@ -56,7 +56,7 @@ module Register
|
||||
@input =s(:call, :putstr , s(:arguments, s(:string, "Hello") ) )
|
||||
@expect = [Label, SlotToReg, SlotToReg, RegToSlot, LoadConstant, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, SlotToReg, RegToSlot ,
|
||||
LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label, RegisterTransfer ,
|
||||
LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label, RiscTransfer ,
|
||||
SlotToReg, SlotToReg, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
FunctionReturn]
|
||||
was = check_return
|
||||
|
@ -1,12 +1,12 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestFields < MiniTest::Test
|
||||
include ExpressionHelper
|
||||
include AST::Sexp
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
end
|
||||
|
||||
def test_field_not_defined
|
||||
@ -26,7 +26,7 @@ module Register
|
||||
add_space_field(:bro,:Object)
|
||||
@root = :field_access
|
||||
@input = s(:field_access,s(:receiver, s(:known, :self)),s(:field,s(:ivar, :bro)))
|
||||
@output = Register::RegisterValue
|
||||
@output = Risc::RiscValue
|
||||
check
|
||||
end
|
||||
|
||||
|
@ -1,7 +1,7 @@
|
||||
require_relative 'helper'
|
||||
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestFieldStatement < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
@ -23,8 +23,8 @@ module Register
|
||||
|
||||
@expect = [Label, SlotToReg, SlotToReg, RegToSlot, LoadConstant, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, SlotToReg, SlotToReg, SlotToReg ,
|
||||
RegToSlot, LoadConstant, RegToSlot, RegisterTransfer, FunctionCall, Label ,
|
||||
RegisterTransfer, SlotToReg, SlotToReg, RegToSlot, LoadConstant, SlotToReg ,
|
||||
RegToSlot, LoadConstant, RegToSlot, RiscTransfer, FunctionCall, Label ,
|
||||
RiscTransfer, SlotToReg, SlotToReg, RegToSlot, LoadConstant, SlotToReg ,
|
||||
RegToSlot, Label, FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
@ -33,7 +33,7 @@ module Register
|
||||
Parfait.object_space.get_main.add_local(:name , :Word)
|
||||
@input = s(:statements, s(:l_assignment, s(:local, :name), s(:field_access, s(:receiver, s(:known, :message)), s(:field, s(:ivar, :name)))), s(:return, s(:local, :name)))
|
||||
|
||||
@expect = [Label, RegisterTransfer, SlotToReg, SlotToReg, RegToSlot, SlotToReg ,
|
||||
@expect = [Label, RiscTransfer, SlotToReg, SlotToReg, RegToSlot, SlotToReg ,
|
||||
SlotToReg, RegToSlot, LoadConstant, SlotToReg, RegToSlot, Label ,
|
||||
FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative 'helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestIfStatement < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
|
@ -1,32 +1,32 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestFields < MiniTest::Test
|
||||
include ExpressionHelper
|
||||
include AST::Sexp
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
end
|
||||
|
||||
def test_local
|
||||
Parfait.object_space.get_main.add_local(:bar , :Integer)
|
||||
@input = s(:local, :bar)
|
||||
@output = Register::RegisterValue
|
||||
@output = Risc::RiscValue
|
||||
check
|
||||
end
|
||||
|
||||
def test_space
|
||||
@root = :name
|
||||
@input = s(:known, :space)
|
||||
@output = Register::RegisterValue
|
||||
@output = Risc::RiscValue
|
||||
check
|
||||
end
|
||||
|
||||
def test_args
|
||||
Parfait.object_space.get_main.add_argument(:bar , :Integer)
|
||||
@input = s(:arg, :bar)
|
||||
@output = Register::RegisterValue
|
||||
@output = Risc::RiscValue
|
||||
check
|
||||
end
|
||||
|
||||
|
@ -1,14 +1,14 @@
|
||||
require_relative "helper"
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestOps < MiniTest::Test
|
||||
include ExpressionHelper
|
||||
include AST::Sexp
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@root = :operator_value
|
||||
@output = Register::RegisterValue
|
||||
@output = Risc::RiscValue
|
||||
end
|
||||
|
||||
def operators
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative 'helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestReturnStatement < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
@ -30,8 +30,8 @@ module Register
|
||||
def test_return_call
|
||||
@input =s(:statements, s(:return, s(:call, :main, s(:arguments))))
|
||||
@expect = [Label, SlotToReg, SlotToReg, RegToSlot, LoadConstant, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RegisterTransfer ,
|
||||
FunctionCall, Label, RegisterTransfer, SlotToReg, SlotToReg, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, LoadConstant, RegToSlot, RiscTransfer ,
|
||||
FunctionCall, Label, RiscTransfer, SlotToReg, SlotToReg, RegToSlot ,
|
||||
LoadConstant, SlotToReg, RegToSlot, Label, FunctionReturn]
|
||||
assert_nil msg = check_nil , msg
|
||||
end
|
||||
|
@ -1,6 +1,6 @@
|
||||
require_relative 'helper'
|
||||
|
||||
module Register
|
||||
module Risc
|
||||
class TestWhile < MiniTest::Test
|
||||
include Statements
|
||||
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class BasicType < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@mess = @space.first_message
|
||||
assert @mess
|
||||
@ -58,7 +58,7 @@ class BasicType < MiniTest::Test
|
||||
|
||||
# not really parfait test, but related and no other place currently
|
||||
def test_reg_index
|
||||
message_ind = Register.resolve_to_index( :message , :receiver )
|
||||
message_ind = Risc.resolve_to_index( :message , :receiver )
|
||||
assert_equal 3 , message_ind
|
||||
@mess.set_receiver( 55)
|
||||
assert_equal 55 , @mess.get_internal_word(message_ind)
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TypeHash < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@types = @space.instance_variable_get("@types")
|
||||
@first = @types.values.first
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TypeMessages < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@mess = @space.first_message
|
||||
end
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TestMethodApi < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
@try_class = @space.create_class( :Try )
|
||||
@try_type = @try_class.instance_type
|
||||
|
@ -3,7 +3,7 @@ require_relative "../helper"
|
||||
class TypeApi < MiniTest::Test
|
||||
|
||||
def setup
|
||||
Register.machine.boot
|
||||
Risc.machine.boot
|
||||
@space = Parfait.object_space
|
||||
tc = @space.get_class_by_name( :NamedList )
|
||||
@type = tc.instance_type
|
||||
|
Loading…
x
Reference in New Issue
Block a user