/** * Interpret a function call. * * @param environment The environment to make the interpretation of a call * over. This could be another function environment. * We use it to parse arguments in and to obtain the * global environment. * @param function_element The function we want to evaluate the call of. * @param parms The container of parameters into the call. * * * @return The interpreted element. */ Element Function_::InterpretCall( Environment& environment , Element const& function_element , std::vector<Element> const& parms ) { GlobalEnvironment globals(environment.Globals()); bool hasFunction = false; Function function = CastToFunction(function_element, hasFunction); Element result; if (hasFunction) { bool tailRecursion = true; std::vector<Element> parameters(parms); while(tailRecursion) { tailRecursion = false; Environment function_environment = Environment::Create(globals); globals.PushCallStack(function, function_environment); bool success = Funcall_::CreateEnvironment( function.Arguments() , parameters , function_environment ); if (success) { Element body(function.Body()); result = body.Interpret(function_environment); // Making a recursive call using tail recursion. if (Types::TAILRECURSE == result.Type()) { TailRecurse tailRecurse = CastToTailRecurse(result, success); parameters = tailRecurse.Parameters(); // Go again! :D tailRecursion = true; } } globals.PopCallStack(); } } return result; }