// ECMA 15.3.2 The Function Constructor JSObject* constructFunction(ExecState* exec, const ArgList& args, const Identifier& functionName, const UString& sourceURL, int lineNumber) { UString program; if (args.isEmpty()) program = "(function(){})"; else if (args.size() == 1) program = "(function(){" + args.at(exec, 0)->toString(exec) + "})"; else { program = "(function(" + args.at(exec, 0)->toString(exec); for (size_t i = 1; i < args.size() - 1; i++) program += "," + args.at(exec, i)->toString(exec); program += "){" + args.at(exec, args.size() - 1)->toString(exec) + "})"; } int errLine; UString errMsg; SourceCode source = makeSource(program, sourceURL, lineNumber); RefPtr<ProgramNode> programNode = exec->globalData().parser->parse<ProgramNode>(exec, exec->dynamicGlobalObject()->debugger(), source, &errLine, &errMsg); FunctionBodyNode* body = functionBody(programNode.get()); if (!body) return throwError(exec, SyntaxError, errMsg, errLine, source.provider()->asID(), source.provider()->url()); JSGlobalObject* globalObject = exec->lexicalGlobalObject(); ScopeChain scopeChain(globalObject, globalObject->globalData(), exec->globalThisValue()); return new (exec) JSFunction(exec, functionName, body, scopeChain.node()); }
Expression *TypeCompiler::visit(FunctionLiteral *literal) { lmAssert(!literal->classDecl, "local function belongs to a class"); inLocalFunction++; FunctionLiteral *lastFunctionLiteral = currentFunctionLiteral; currentFunctionLiteral = literal; char funcname[256]; snprintf(funcname, 250, "__ls_localfunction%i", functioncount++); ExpDesc v; BC::newLocalVar(cs, funcname, 0); BC::initExpDesc(&v, VLOCAL, cs->fs->freereg); BC::reserveRegs(cs->fs, 1); BC::adjustLocalVars(cs, 1); // store funcinfo // setup closure info here so it is captured as an upvalue, must be unique char funcinfo[256]; snprintf(funcinfo, 250, "__ls_funcinfo_numargs_%i", literal->childIndex); ExpDesc funcInfo; ExpDesc value; BC::singleVar(cs, &funcInfo, funcinfo); BC::initExpDesc(&value, VKNUM, 0); value.u.nval = 0; if (literal->parameters) { value.u.nval = (int)literal->parameters->size(); } BC::storeVar(cs->fs, &funcInfo, &value); ExpDesc closure; functionBody(&closure, literal, literal->lineNumber); BC::storeVar(cs->fs, &v, &closure); literal->e = v; inLocalFunction--; currentFunctionLiteral = lastFunctionLiteral; return literal; }