private void JumpToFunction() { AST_FunctionDefinitionNode functionDefinitionNode = (CurrentNode as AST_FunctionCall).FunctionDefinitionRef; string functionName = functionDefinitionNode.getChild(1).getTokenString(); int nrOfParameters = functionDefinitionNode.getChild(2).getChildren().Count; ReturnValue[] parameters = new ReturnValue[nrOfParameters]; for (int i = nrOfParameters - 1; i >= 0; i--) { parameters[i] = PopValue(); } if (m_externalFunctionCreator.externalFunctions.ContainsKey(functionName)) { //Console.WriteLine("Calling external function " + functionName); ExternalFunctionCreator.OnFunctionCall fc = m_externalFunctionCreator.externalFunctions[functionName]; ReturnValue rv = fc(parameters); if (rv.getReturnValueType() != ReturnValueType.VOID) { PushValue(rv); } } else { PushNewScope(functionDefinitionNode.getScope(), functionName + "_memorySpace" + functionCounter++, functionDefinitionNode); for (int i = nrOfParameters - 1; i >= 0; i--) { PushValue(parameters[i]); // reverse order } } }
private void JumpToFunction() { AST_FunctionDefinitionNode functionDefinitionNode = (CurrentNode as AST_FunctionCall).FunctionDefinitionRef; string functionName = functionDefinitionNode.getChild(1).getTokenString(); #if BUILT_IN_PROFILING ProfileData data = null; if (m_profileData.TryGetValue(functionName, out data)) { data.calls++; } else { m_profileData.Add(functionName, new ProfileData() { calls = 1, totalTime = 0f, }); } #endif var parameterDefs = functionDefinitionNode.getChild(2).getChildren(); //ASTPainter painter = new ASTPainter(); int nrOfParameters = parameterDefs.Count; object[] parameters = new object[nrOfParameters]; for (int i = nrOfParameters - 1; i >= 0; i--) { //painter.PaintAST(parameterDefs[i]); var paramDef = parameterDefs[i]; var declaration = paramDef.getChild(0) as AST_VariableDeclaration; parameters[i] = ReturnValueConversions.ChangeTypeBasedOnReturnValueType(PopValue(), declaration.Type); } //try { if (IsFunctionExternal(functionName)) { CallExternalFunction(functionName, parameters); } else { PushNewScope(functionDefinitionNode.getScope(), functionName + "_memorySpace" + functionCounter++, functionDefinitionNode); for (int i = nrOfParameters - 1; i >= 0; i--) { PushValue(parameters[i]); // reverse order } } // } // catch(Exception e) { // Console.WriteLine("Exception when calling " + functionName + ": " + e.StackTrace); // throw e; // } }
private void evaluateReferencesForFUNCTION_CALL(AST tree) { // Function name: string functionName = tree.getTokenString(); var sym = m_currentScope.resolve(functionName); FunctionSymbol function = sym as FunctionSymbol; if (function == null) { m_errorHandler.errorOccured("Can't find function with name " + functionName, Error.ErrorType.SCOPE, tree.getToken().LineNr, tree.getToken().LinePosition ); } else { #if WRITE_DEBUG_INFO Console.WriteLine("Resolved function call with name " + functionName + " (on line " + tree.getToken().LineNr + ")"); #endif // Parameters evaluateReferencesInAllChildren(tree); AST node = function.getFunctionDefinitionNode(); AST_FunctionDefinitionNode functionDefinitionTree = (AST_FunctionDefinitionNode)(node); /*if(functionDefinitionTree.getTokenString() != "<EXTERNAL_FUNC_DECLARATION>") { * evaluateReferencesForFUNC_DECLARATION(functionDefinitionTree); * }*/ // Setup reference to Function Definition AST node AST_FunctionCall functionCallAst = tree as AST_FunctionCall; Debug.Assert(functionCallAst != null); functionCallAst.FunctionDefinitionRef = functionDefinitionTree; List <AST> calleeParameterList = functionDefinitionTree.getChild(2).getChildren(); // Check that the number of arguments is right AST callerParameterList = tree.getChild(0); List <AST> arguments = callerParameterList.getChildren(); if (arguments.Count != calleeParameterList.Count) { m_errorHandler.errorOccured( "Wrong nr of arguments to '" + functionDefinitionTree.getChild(1).getTokenString() + "' , expected " + calleeParameterList.Count + " but got " + arguments.Count , Error.ErrorType.SYNTAX, tree.getToken().LineNr, tree.getToken().LinePosition); } } }
/// <summary> /// Sets the program to execute function. /// Returns true if the program had the function. /// </summary> public ProgramFunctionCallStatus SetProgramToExecuteFunction(string functionName, object[] args) { //Console.WriteLine ("Will execute '" + functionName + "' in global scope '" + m_globalScope + "'"); FunctionSymbol functionSymbol = (FunctionSymbol)m_globalScope.resolve(functionName); //Console.WriteLine("Found function symbol: " + functionSymbol.ToString()); if (functionSymbol == null) { return(ProgramFunctionCallStatus.NO_FUNCTION); } if (IsFunctionExternal(functionName)) { CallExternalFunction(functionName, args); return(ProgramFunctionCallStatus.EXTERNAL_FUNCTION); } else { AST_FunctionDefinitionNode functionDefinitionNode = (AST_FunctionDefinitionNode)functionSymbol.getFunctionDefinitionNode(); if (functionDefinitionNode != null) { var parameters = functionDefinitionNode.getChild(2).getChildren(); int nrOfParameters = parameters.Count; if (nrOfParameters != args.Length) { throw new Error("The function " + functionName + " takes " + nrOfParameters + " arguments, not " + args.Length); } Reset(); m_topLevelDepth = 1; m_currentScope = functionDefinitionNode.getScope(); m_currentScope.ClearMemorySpaces(); string nameOfNewMemorySpace = functionName + "_memorySpace" + functionCounter++; PushNewScope(functionDefinitionNode.getScope(), nameOfNewMemorySpace, functionDefinitionNode); for (int i = args.Length - 1; i >= 0; i--) { var declaration = parameters[i].getChild(0) as AST_VariableDeclaration; object convertedValue = ReturnValueConversions.ChangeTypeBasedOnReturnValueType(args[i], declaration.Type); PushValue(convertedValue); // reverse order } //Console.WriteLine ("Ready to start running function '" + functionName + "' with memory space '" + nameOfNewMemorySpace + "'"); } else { throw new Error(functionName + " has got no function definition node!"); } } return(ProgramFunctionCallStatus.NORMAL_FUNCTION); // all went well (starting the function) }