Search in sources :

Example 21 with FunctionNode

use of org.mozilla.javascript.ast.FunctionNode in project st-js by st-js.

the class RhinoJavaScriptBuilder method function.

/**
 * {@inheritDoc}
 */
@Override
public AstNode function(String name, Iterable<AstNode> params, AstNode body) {
    FunctionNode func = new FunctionNode();
    if (name != null) {
        func.setFunctionName((Name) name(name));
    }
    func.setParams(list(params));
    if (body == null) {
        func.setBody(new Block());
    } else if (body instanceof Block) {
        func.setBody(body);
    } else {
        func.setBody(addStatement(null, body));
    }
    return func;
}
Also used : FunctionNode(org.mozilla.javascript.ast.FunctionNode) Block(org.mozilla.javascript.ast.Block)

Example 22 with FunctionNode

use of org.mozilla.javascript.ast.FunctionNode in project HL4A by HL4A.

the class IRFactory method initFunction.

private Node initFunction(FunctionNode fnNode, int functionIndex, Node statements, int functionType) {
    fnNode.setFunctionType(functionType);
    fnNode.addChildToBack(statements);
    int functionCount = fnNode.getFunctionCount();
    if (functionCount != 0) {
        // Functions containing other functions require activation objects
        fnNode.setRequiresActivation();
    }
    if (functionType == FunctionNode.FUNCTION_EXPRESSION) {
        Name name = fnNode.getFunctionName();
        if (name != null && name.length() != 0 && fnNode.getSymbol(name.getIdentifier()) == null) {
            // A function expression needs to have its name as a
            // variable (if it isn't already allocated as a variable).
            // See ECMA Ch. 13.  We add code to the beginning of the
            // function to initialize a local variable of the
            // function's name to the function value, but only if the
            // function doesn't already define a formal parameter, var,
            // or nested function with the same name.
            fnNode.putSymbol(new Symbol(Token.FUNCTION, name.getIdentifier()));
            Node setFn = new Node(Token.EXPR_VOID, new Node(Token.SETNAME, Node.newString(Token.BINDNAME, name.getIdentifier()), new Node(Token.THISFN)));
            statements.addChildrenToFront(setFn);
        }
    }
    // Add return to end if needed.
    Node lastStmt = statements.getLastChild();
    if (lastStmt == null || lastStmt.getType() != Token.RETURN) {
        statements.addChildToBack(new Node(Token.RETURN));
    }
    Node result = Node.newString(Token.FUNCTION, fnNode.getName());
    result.putIntProp(Node.FUNCTION_PROP, functionIndex);
    return result;
}
Also used : Symbol(org.mozilla.javascript.ast.Symbol) ScriptNode(org.mozilla.javascript.ast.ScriptNode) AstNode(org.mozilla.javascript.ast.AstNode) LetNode(org.mozilla.javascript.ast.LetNode) FunctionNode(org.mozilla.javascript.ast.FunctionNode) Name(org.mozilla.javascript.ast.Name)

Example 23 with FunctionNode

use of org.mozilla.javascript.ast.FunctionNode in project HL4A by HL4A.

the class IRFactory method transformFunction.

private Node transformFunction(FunctionNode fn) {
    int functionType = fn.getFunctionType();
    int start = decompiler.markFunctionStart(functionType);
    Node mexpr = decompileFunctionHeader(fn);
    int index = currentScriptOrFn.addFunction(fn);
    PerFunctionVariables savedVars = new PerFunctionVariables(fn);
    try {
        // If we start needing to record much more codegen metadata during
        // function parsing, we should lump it all into a helper class.
        Node destructuring = (Node) fn.getProp(Node.DESTRUCTURING_PARAMS);
        fn.removeProp(Node.DESTRUCTURING_PARAMS);
        int lineno = fn.getBody().getLineno();
        // only for body, not params
        ++nestingOfFunction;
        Node body = transform(fn.getBody());
        if (!fn.isExpressionClosure()) {
            decompiler.addToken(Token.RC);
        }
        fn.setEncodedSourceBounds(start, decompiler.markFunctionEnd(start));
        if (functionType != FunctionNode.FUNCTION_EXPRESSION && !fn.isExpressionClosure()) {
            // Add EOL only if function is not part of expression
            // since it gets SEMI + EOL from Statement in that case
            decompiler.addToken(Token.EOL);
        }
        if (destructuring != null) {
            body.addChildToFront(new Node(Token.EXPR_VOID, destructuring, lineno));
        }
        int syntheticType = fn.getFunctionType();
        Node pn = initFunction(fn, index, body, syntheticType);
        if (mexpr != null) {
            pn = createAssignment(Token.ASSIGN, mexpr, pn);
            if (syntheticType != FunctionNode.FUNCTION_EXPRESSION) {
                pn = createExprStatementNoReturn(pn, fn.getLineno());
            }
        }
        return pn;
    } finally {
        --nestingOfFunction;
        savedVars.restore();
    }
}
Also used : ScriptNode(org.mozilla.javascript.ast.ScriptNode) AstNode(org.mozilla.javascript.ast.AstNode) LetNode(org.mozilla.javascript.ast.LetNode) FunctionNode(org.mozilla.javascript.ast.FunctionNode)

Example 24 with FunctionNode

use of org.mozilla.javascript.ast.FunctionNode in project HL4A by HL4A.

the class CodeGenerator method generateNestedFunctions.

private void generateNestedFunctions() {
    int functionCount = scriptOrFn.getFunctionCount();
    if (functionCount == 0)
        return;
    InterpreterData[] array = new InterpreterData[functionCount];
    for (int i = 0; i != functionCount; i++) {
        FunctionNode fn = scriptOrFn.getFunctionNode(i);
        CodeGenerator gen = new CodeGenerator();
        gen.compilerEnv = compilerEnv;
        gen.scriptOrFn = fn;
        gen.itsData = new InterpreterData(itsData);
        gen.generateFunctionICode();
        array[i] = gen.itsData;
    }
    itsData.itsNestedFunctions = array;
}
Also used : FunctionNode(org.mozilla.javascript.ast.FunctionNode)

Example 25 with FunctionNode

use of org.mozilla.javascript.ast.FunctionNode in project HL4A by HL4A.

the class CodeGenerator method generateFunctionICode.

private void generateFunctionICode() {
    itsInFunctionFlag = true;
    FunctionNode theFunction = (FunctionNode) scriptOrFn;
    itsData.itsFunctionType = theFunction.getFunctionType();
    itsData.itsNeedsActivation = theFunction.requiresActivation();
    if (theFunction.getFunctionName() != null) {
        itsData.itsName = theFunction.getName();
    }
    if (theFunction.isGenerator()) {
        addIcode(Icode_GENERATOR);
        addUint16(theFunction.getBaseLineno() & 0xFFFF);
    }
    if (theFunction.isInStrictMode()) {
        itsData.isStrict = true;
    }
    generateICodeFromTree(theFunction.getLastChild());
}
Also used : FunctionNode(org.mozilla.javascript.ast.FunctionNode)

Aggregations

FunctionNode (org.mozilla.javascript.ast.FunctionNode)32 ScriptNode (org.mozilla.javascript.ast.ScriptNode)20 AstNode (org.mozilla.javascript.ast.AstNode)8 Name (org.mozilla.javascript.ast.Name)7 LetNode (org.mozilla.javascript.ast.LetNode)6 Jump (org.mozilla.javascript.ast.Jump)4 Scope (org.mozilla.javascript.ast.Scope)4 XmlString (org.mozilla.javascript.ast.XmlString)3 HashMap (java.util.HashMap)2 HashSet (java.util.HashSet)2 Iterator (java.util.Iterator)2 Map (java.util.Map)2 AstRoot (org.mozilla.javascript.ast.AstRoot)2 ErrorNode (org.mozilla.javascript.ast.ErrorNode)2 Block (org.mozilla.javascript.ast.Block)1 Comment (org.mozilla.javascript.ast.Comment)1 EmptyExpression (org.mozilla.javascript.ast.EmptyExpression)1 ExpressionStatement (org.mozilla.javascript.ast.ExpressionStatement)1 ObjectProperty (org.mozilla.javascript.ast.ObjectProperty)1 ParenthesizedExpression (org.mozilla.javascript.ast.ParenthesizedExpression)1