rubyx/lib/bosl/compiler/function_expression.rb
Torsten Ruger f4a4ccb98e several larger changes came together, bit of cleaning too
- all code must be in functions (which must be in classes).
— changes a fair few tests
— also changes api, as method is not recursive, not passed around
- all state in instance vars in compiler (no accessors)
- class is another such variable, surely more coming
all green again
2015-10-06 00:27:13 +03:00

55 lines
1.6 KiB
Ruby

module Bosl
Compiler.class_eval do
def on_function expression
#puts expression.inspect
return_type , name , parameters, kids , receiver = *expression
name = name.to_a.first
args = parameters.to_a.collect do |p|
raise "error, argument must be a identifier, not #{p}" unless p.type == :parameter
Parfait::Variable.new( *p)
end
if receiver
# compiler will always return slot. with known value or not
r = receiver.first
if( r.is_a? Parfait::Class )
class_name = r.value.name
else
if( r != :self)
raise "unimplemented case in function #{r}"
else
r = Virtual::Self.new()
class_name = method.for_class.name
end
end
else
r = @clazz
class_name = @clazz.name
end
raise "Already in method #{@method}" if @method
@method = @clazz.get_instance_method( name )
if(@method)
puts "Warning, redefining method #{name}" unless name == :main
#TODO check args / type compatibility
@method.source.init @method
else
@method = Virtual::MethodSource.create_method(class_name, return_type, name , args )
@method.for_class.add_instance_method @method
end
@method.source.receiver = r
puts "compile method #{@method.name}"
#frame = frame.new_frame
kids.to_a.each do |ex|
return_type = process(ex)
raise return_type.inspect if return_type.is_a? Virtual::Instruction
end
@method.source.return_type = return_type
@method = nil
Virtual::Return.new(return_type)
end
end
end