@Override public boolean enterWithNode(final WithNode withNode) { enterDefault(withNode); type("WithStatement"); comma(); property("object"); withNode.getExpression().accept(this); comma(); property("body"); withNode.getBody().accept(this); return leave(); }
/** * WithStatement : * with ( Expression ) Statement * * See 12.10 * * Parse WITH statement. */ private void withStatement() { // Capture WITH token. final int withLine = line; final long withToken = token; // WITH tested in caller. next(); // ECMA 12.10.1 strict mode restrictions if (isStrictMode) { throw error(AbstractParser.message("strict.no.with"), withToken); } expect(LPAREN); final Expression expression = expression(); expect(RPAREN); final Block body = getStatement(); appendStatement(new WithNode(withLine, withToken, finish, expression, body)); }
/** * WithStatement : * with ( Expression ) Statement * * See 12.10 * * Parse WITH statement. */ private void withStatement() { // Capture WITH token. final int withLine = line; final long withToken = token; // WITH tested in caller. next(); // ECMA 12.10.1 strict mode restrictions if (isStrictMode) { throw error(AbstractParser.message("strict.no.with"), withToken); } // Get WITH expression. WithNode withNode = new WithNode(withLine, withToken, finish); try { lc.push(withNode); expect(LPAREN); withNode = withNode.setExpression(lc, expression()); expect(RPAREN); withNode = withNode.setBody(lc, getStatement()); } finally { lc.pop(withNode); } appendStatement(withNode); }
@Override public boolean enterWithNode(final WithNode withNode) { withNode.toString(sb, printTypes); withNode.getBody().accept(this); return false; }
/** * Determines if the symbol has to be a scope symbol. In general terms, it has to be a scope symbol if it can only * be reached from the current block by traversing a function node, a split node, or a with node. * @param symbol the symbol checked for needing to be a scope symbol * @return true if the symbol has to be a scope symbol. */ private boolean symbolNeedsToBeScope(final Symbol symbol) { if (symbol.isThis() || symbol.isInternal()) { return false; } final FunctionNode func = lc.getCurrentFunction(); if ( func.allVarsInScope() || (!symbol.isBlockScoped() && func.isProgram())) { return true; } boolean previousWasBlock = false; for (final Iterator<LexicalContextNode> it = lc.getAllNodes(); it.hasNext();) { final LexicalContextNode node = it.next(); if (node instanceof FunctionNode || isSplitArray(node)) { // We reached the function boundary or a splitting boundary without seeing a definition for the symbol. // It needs to be in scope. return true; } else if (node instanceof WithNode) { if (previousWasBlock) { // We reached a WithNode; the symbol must be scoped. Note that if the WithNode was not immediately // preceded by a block, this means we're currently processing its expression, not its body, // therefore it doesn't count. return true; } previousWasBlock = false; } else if (node instanceof Block) { if (((Block)node).getExistingSymbol(symbol.getName()) == symbol) { // We reached the block that defines the symbol without reaching either the function boundary, or a // WithNode. The symbol need not be scoped. return false; } previousWasBlock = true; } else { previousWasBlock = false; } } throw new AssertionError(); }
@Override public boolean enterWithNode(final WithNode withNode) { curStat = new WithTreeImpl(withNode, translateExpr(withNode.getExpression()), translateBlock(withNode.getBody())); return false; }
/** * Determines if the symbol has to be a scope symbol. In general terms, it has to be a scope symbol if it can only * be reached from the current block by traversing a function node, a split node, or a with node. * @param symbol the symbol checked for needing to be a scope symbol * @return true if the symbol has to be a scope symbol. */ private boolean symbolNeedsToBeScope(final Symbol symbol) { if (symbol.isThis() || symbol.isInternal()) { return false; } final FunctionNode func = lc.getCurrentFunction(); if ( func.allVarsInScope() || (!symbol.isBlockScoped() && func.isProgram())) { return true; } boolean previousWasBlock = false; for (final Iterator<LexicalContextNode> it = lc.getAllNodes(); it.hasNext();) { final LexicalContextNode node = it.next(); if (node instanceof FunctionNode || isSplitLiteral(node)) { // We reached the function boundary or a splitting boundary without seeing a definition for the symbol. // It needs to be in scope. return true; } else if (node instanceof WithNode) { if (previousWasBlock) { // We reached a WithNode; the symbol must be scoped. Note that if the WithNode was not immediately // preceded by a block, this means we're currently processing its expression, not its body, // therefore it doesn't count. return true; } previousWasBlock = false; } else if (node instanceof Block) { if (((Block)node).getExistingSymbol(symbol.getName()) == symbol) { // We reached the block that defines the symbol without reaching either the function boundary, or a // WithNode. The symbol need not be scoped. return false; } previousWasBlock = true; } else { previousWasBlock = false; } } throw new AssertionError(); }
@Override public boolean enterWithNode(final WithNode withNode) { if (reachable) { visitExpression(withNode.getExpression()); withNode.getBody().accept(this); } return false; }
/** * Determines if the symbol has to be a scope symbol. In general terms, it * has to be a scope symbol if it can only be reached from the current block * by traversing a function node, a split node, or a with node. * * @param symbol the symbol checked for needing to be a scope symbol * @return true if the symbol has to be a scope symbol. */ private boolean symbolNeedsToBeScope(final Symbol symbol) { if (symbol.isThis() || symbol.isInternal()) { return false; } final FunctionNode func = lc.getCurrentFunction(); if (func.allVarsInScope() || (!symbol.isBlockScoped() && func.isProgram())) { return true; } boolean previousWasBlock = false; for (final Iterator<LexicalContextNode> it = lc.getAllNodes(); it.hasNext();) { final LexicalContextNode node = it.next(); if (node instanceof FunctionNode || isSplitLiteral(node)) { // We reached the function boundary or a splitting boundary without seeing a definition for the symbol. // It needs to be in scope. return true; } else if (node instanceof WithNode) { if (previousWasBlock) { // We reached a WithNode; the symbol must be scoped. Note that if the WithNode was not immediately // preceded by a block, this means we're currently processing its expression, not its body, // therefore it doesn't count. return true; } previousWasBlock = false; } else if (node instanceof Block) { if (((Block) node).getExistingSymbol(symbol.getName()) == symbol) { // We reached the block that defines the symbol without reaching either the function boundary, or a // WithNode. The symbol need not be scoped. return false; } previousWasBlock = true; } else { previousWasBlock = false; } } throw new AssertionError(); }