introducing expressions and constants

not everything statement anymore (as in ruby)
basic statement tests working, rest havoc
This commit is contained in:
Torsten Ruger
2018-03-15 11:24:14 +05:30
parent 163cad456f
commit 78ef1368de
17 changed files with 112 additions and 69 deletions

View File

@ -4,7 +4,7 @@ module Mom
# the a is an instance variable on the current frame, and the frame is an instance
# of the current message, so the effect is something like message.frame.a = 5
# @left: See SlotLoad, an array of symbols
# @right: A Constant from parse, ie an instance of classes in basc_value, like TrueStatement
# @right: A Constant from parse, ie an instance of classes in basc_value, like TrueConstant
class SlotConstant < SlotLoad
def initialize(left , right)

View File

@ -38,31 +38,31 @@ module Vool
#basic Values
def on_self exp
SelfStatement.new
SelfExpression.new
end
def on_nil expression
NilStatement.new
NilConstant.new
end
def on_int expression
IntegerStatement.new(expression.children.first)
IntegerConstant.new(expression.children.first)
end
def on_float expression
FloatStatement.new(expression.children.first)
FloatConstant.new(expression.children.first)
end
def on_true expression
TrueStatement.new
TrueConstant.new
end
def on_false expression
FalseStatement.new
FalseConstant.new
end
def on_str expression
StringStatement.new(expression.children.first)
StringConstant.new(expression.children.first)
end
alias :on_string :on_str
@ -72,7 +72,7 @@ module Vool
alias :on_xstr :on_dstr
def on_sym expression
SymbolStatement.new(expression.children.first)
SymbolConstant.new(expression.children.first)
end
alias :on_string :on_str
@ -151,7 +151,7 @@ module Vool
def on_send statement
kids = statement.children.dup
receiver = process(kids.shift) || SelfStatement.new
receiver = process(kids.shift) || SelfExpression.new
name = kids.shift
arguments = process_all(kids)
SendStatement.new( name , receiver , arguments )
@ -167,14 +167,14 @@ module Vool
# this is a call to super without args (z = zero arity)
def on_zsuper exp
SendStatement.new( nil , SuperStatement.new , nil)
SendStatement.new( nil , SuperExpression.new , nil)
end
# this is a call to super with args and
# same name as current method, which is set later
def on_super( statement )
arguments = process_all(statement.children)
SendStatement.new( nil , SuperStatement.new , arguments)
SendStatement.new( nil , SuperExpression.new , arguments)
end
def on_assignment statement

View File

@ -10,6 +10,9 @@
# Also, Vool is a typed tree, not abstract, so there is a base class Statement
# and all it's derivation that make up the syntax tree
#
# Also Vool has expression and statements and simple syntax. So returns must be explicit
# not everthing is just assignable, ifs can only test simple expressions etc (wip)
#
# This allows us to write compilers or passes of the compiler(s) as functions on the
# classes.
#
@ -22,6 +25,13 @@ module Vool
#
class Statement
# after creation vool normalizes to ensure valid syntax and simplify
# also throw errors if violation
def normalize
return self
end
# flatten tree to array
def collect(arr)
arr << self
end
@ -51,6 +61,10 @@ module Vool
def set_class( clazz )
end
end
class Expression
end
end
@ -61,7 +75,7 @@ require_relative "statements/class_statement"
require_relative "statements/hash_statement"
require_relative "statements/if_statement"
require_relative "statements/logical_statement"
require_relative "statements/local_statement"
require_relative "statements/local_assignment"
require_relative "statements/method_statement"
require_relative "statements/return_statement"
require_relative "statements/statements"

View File

@ -5,6 +5,14 @@ module Vool
def initialize(name , value )
@name , @value = name , value
end
def normalize()
raise "not named left #{name}" unless @name.is_a?(Named)
raise "unsupported right #{value}" unless @name.is_a?(Named) or
@name.is_a?(SendStatement) or @name.is_a?(Constant)
self
end
def collect(arr)
@value.collect(arr)
super

View File

@ -4,13 +4,13 @@ module Vool
Mom::SlotMove
end
end
class ConstantStatement < Statement
class Constant < Expression
def slot_class
Mom::SlotConstant
end
end
class IntegerStatement < ConstantStatement
class IntegerConstant < Constant
attr_reader :value
def initialize(value)
@value = value
@ -22,7 +22,7 @@ module Vool
Parfait.object_space.get_class_by_name(:Integer).instance_type
end
end
class FloatStatement < ConstantStatement
class FloatConstant < Constant
attr_reader :value
def initialize(value)
@value = value
@ -31,22 +31,22 @@ module Vool
true
end
end
class TrueStatement < ConstantStatement
class TrueConstant < Constant
def ct_type
Parfait.object_space.get_class_by_name(:True).instance_type
end
end
class FalseStatement < ConstantStatement
class FalseConstant < Constant
def ct_type
Parfait.object_space.get_class_by_name(:False).instance_type
end
end
class NilStatement < ConstantStatement
class NilConstant < Constant
def ct_type
Parfait.object_space.get_class_by_name(:Nil).instance_type
end
end
class SelfStatement < Statement
class SelfExpression < Expression
attr_reader :clazz
def set_class(clazz)
@clazz = clazz
@ -58,9 +58,9 @@ module Vool
@clazz.instance_type
end
end
class SuperStatement < Statement
class SuperExpression < Statement
end
class StringStatement < ConstantStatement
class StringConstant < Constant
attr_reader :value
def initialize(value)
@value = value
@ -72,7 +72,7 @@ module Vool
Parfait.object_space.get_class_by_name(:Word).instance_type
end
end
class SymbolStatement < StringStatement
class SymbolConstant < StringConstant
def ct_type
Parfait.object_space.get_class_by_name(:Word).instance_type
end

View File

@ -1,10 +0,0 @@
module Vool
module Hoister
def hoist_condition( method )
return [@condition] if @condition.is_a?(Vool::Named)
local = method.create_tmp
assign = LocalAssignment.new( local , @condition)
[Vool::LocalVariable.new(local) , assign]
end
end
end

View File

@ -1,7 +1,7 @@
require_relative "hoister"
require_relative "normalizer"
module Vool
class IfStatement < Statement
include Hoister
include Normalizer
attr_reader :condition , :if_true , :if_false
@ -12,6 +12,14 @@ module Vool
simplify_condition
end
def normalize(method)
cond , rest = *normalize_name(@condition)
fals = @if_false ? @if_false.normalize(method) : nil
me = IfStatement.new(cond , @if_true.normalize(method), fals)
return me unless rest
rest << me
end
def to_mom( method )
if_true = @if_true.to_mom( method )
if_false = @if_false ? @if_false.to_mom( method ) : nil

View File

@ -0,0 +1,16 @@
module Vool
module Normalizer
# given a something, determine if it is a Name
#
# Return a Name, and a possible rest that has a hoisted part of the statement
#
# eg if( @var % 5) is not normalized
# but if(tmp_123) is with tmp_123 = @var % 5 hoited above the if
def normalize_name( method )
return [@condition] if @condition.is_a?(Named)
local = method.create_tmp
assign = LocalAssignment.new( local , @condition)
[LocalVariable.new(local) , assign]
end
end
end

View File

@ -96,8 +96,8 @@ module Vool
[Mom::SlotMove.new([@dynamic, :cached_type] , [:receiver , :type])]
end
def build_method_cache_update(in_method)
receiver = StringStatement.new(@name)
resolve = SendStatement.new(:resolve_method , receiver , [SelfStatement.new])
receiver = StringConstant.new(@name)
resolve = SendStatement.new(:resolve_method , receiver , [SelfExpression.new])
move_method = Mom::SlotMove.new([@dynamic, :cached_method] , [:receiver , :return])
resolve.to_mom(in_method) << move_method
end

View File

@ -6,7 +6,7 @@ module Vool
end
end
class LocalVariable < Statement
class LocalVariable < Expression
include Named
def to_mom(method)
if method.args_type.variable_index(@name)
@ -18,7 +18,7 @@ module Vool
end
end
class InstanceVariable < Statement
class InstanceVariable < Expression
include Named
def to_mom(method)
Mom::SlotDefinition.new(:message , [ :receiver , @name] )
@ -29,11 +29,11 @@ module Vool
end
end
class ClassVariable < Statement
class ClassVariable < Expression
include Named
end
class ModuleName < Statement
class ModuleName < Expression
include Named
end
end

View File

@ -1,8 +1,8 @@
require_relative "hoister"
require_relative "normalizer"
module Vool
class WhileStatement < Statement
include Hoister
include Normalizer
attr_reader :condition , :statements
def initialize( condition , statements )
@ -11,6 +11,13 @@ module Vool
simplify_condition
end
def normalize(method)
cond , rest = *normalize_name(@condition)
me = WhileStatement.new(cond , @statements.normalize(method))
return me unless rest
rest << me
end
def to_mom( method )
statements = @statements.to_mom( method )
condition , hoisted = hoist_condition( method )