void ByteCodeVisitor::visitCallNode(mathvm::CallNode *node) { unsigned long stackSize = currStack->size(); AstFunction *astFunction = currScope->lookupFunction(node->name(), true); AstFunctionInfo *functionInfo = (AstFunctionInfo *) astFunction->info(); Scope *parameterScope = astFunction->scope(); if (node->parametersNumber() != parameterScope->variablesCount()) { error("parameters number mistmach in calling %s", node->name().c_str()); } vector<VarType> declaredParameters; declaredParameters.reserve(parameterScope->variablesCount()); Scope::VarIterator varIterator(parameterScope); while (varIterator.hasNext()) { declaredParameters.push_back(varIterator.next()->type()); } vector<VarType>::reverse_iterator it = declaredParameters.rbegin(); for (uint32_t i = node->parametersNumber(); i > 0; --i, ++it) { AstNode *n = node->parameterAt(i - 1); n->visit(this); cast(topStack(), (*it)); } insn(BC_CALL); typed(functionInfo->function->id()); if (astFunction->returnType() != VT_VOID) { pushStack(astFunction->returnType()); } }
void ByteCodeVisitor::visitFunctionNode(mathvm::FunctionNode *node) { BytecodeFunction *dump = currentBytecodeFunction; if (currScope) { AstFunction *function = currScope->lookupFunction(node->name()); if (!function) { error("undeclared function %s", node->name().c_str()); } AstFunctionInfo *astFunctionInfo = (AstFunctionInfo *) function->info(); currentBytecodeFunction = astFunctionInfo->function; } else { currentBytecodeFunction = dynamic_cast<BytecodeFunction *>(interpreterCode->functionById((uint16_t) 0)); } std::vector<VarType> newStack; currStack = &newStack; Scope::VarIterator varIterator(node->body()->scope()->parent()); while (varIterator.hasNext()) { AstVar *var = varIterator.next(); pushStack(var->type());//ensure that variables on stack is ok store(var); } visitBlockNode(node->body()); currentBytecodeFunction = dump; currScope = currScope->parent();//jump parameters scope }