X-Git-Url: http://nitlanguage.org diff --git a/src/interpreter/naive_interpreter.nit b/src/interpreter/naive_interpreter.nit index cd264f1..34fd8f1 100644 --- a/src/interpreter/naive_interpreter.nit +++ b/src/interpreter/naive_interpreter.nit @@ -407,18 +407,24 @@ private class NaiveInterpreter do var initializers = callsite.mpropdef.initializers if not initializers.is_empty then - assert initializers.length == arguments.length - 1 else debug("expected {initializers.length} got {arguments.length - 1}") var recv = arguments.first var i = 1 for p in initializers do if p isa MMethod then - self.send(p, [recv, arguments[i]]) + var args = [recv] + for x in p.intro.msignature.mparameters do + args.add arguments[i] + i += 1 + end + self.send(p, args) else if p isa MAttribute then assert recv isa MutableInstance recv.attributes[p] = arguments[i] + i += 1 else abort - i += 1 end + assert i == arguments.length + return send(callsite.mproperty, [recv]) end return send(callsite.mproperty, arguments) @@ -501,6 +507,10 @@ private class NaiveInterpreter do return mtype.anchor_to(self.mainmodule, self.frame.arguments.first.mtype.as(MClassType)) end + + # Placebo instance used to mark internal error result when `null` already have a meaning. + # TODO: replace with multiple return or something better + var error_instance = new MutableInstance(modelbuilder.model.null_type) is lazy end # An instance represents a value of the executed program. @@ -671,14 +681,28 @@ redef class AMethPropdef v.call_without_varargs(superpd, arguments) end + if mpropdef.is_intern or mpropdef.is_extern then + var res = intern_call(v, mpropdef, arguments) + if res != v.error_instance then return res + end + if n_block != null then v.stmt(self.n_block) return null + end + + if mpropdef.is_intern then + fatal(v, "NOT YET IMPLEMENTED intern {mpropdef}") + else if mpropdef.is_extern then + fatal(v, "NOT YET IMPLEMENTED extern {mpropdef}") else - return intern_call(v, mpropdef, arguments) + fatal(v, "NOT YET IMPLEMENTED {mpropdef}") end + abort end + # Interprets a intern or a shortcut extern method. + # Returns the result for a function, `null` for a procedure, or `error_instance` if the method is unknown. private fun intern_call(v: NaiveInterpreter, mpropdef: MMethodDef, args: Array[Instance]): nullable Instance do var pname = mpropdef.mproperty.name @@ -986,14 +1010,7 @@ redef class AMethPropdef else if pname == "address_is_null" then return v.false_instance end - if mpropdef.is_intern then - fatal(v, "NOT YET IMPLEMENTED intern {mpropdef}") - else if mpropdef.is_extern then - fatal(v, "NOT YET IMPLEMENTED extern {mpropdef}") - else - fatal(v, "NOT YET IMPLEMENTED {mpropdef}") - end - abort + return v.error_instance end end @@ -1060,7 +1077,6 @@ redef class AClassdef private fun call(v: NaiveInterpreter, mpropdef: MMethodDef, args: Array[Instance]): nullable Instance do if mpropdef.mproperty.is_root_init then - assert self.super_inits == null assert args.length == 1 if not mpropdef.is_intro then # standard call-next-method @@ -1068,27 +1084,9 @@ redef class AClassdef v.call_without_varargs(superpd, args) end return null + else + abort end - - var super_inits = self.super_inits - if super_inits != null then - var args_of_super = args - if args.length > 1 then args_of_super = [args.first] - for su in super_inits do - v.send(su, args_of_super) - end - end - var recv = args.first - assert recv isa MutableInstance - var i = 1 - # Collect undefined attributes - for npropdef in self.n_propdefs do - if npropdef isa AAttrPropdef and not npropdef.noinit and npropdef.n_expr == null then - v.write_attribute(npropdef.mpropdef.mproperty, recv, args[i]) - i += 1 - end - end - return null end end