nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/parser/Parser.java
author sundar
Mon, 14 Sep 2015 16:13:10 +0530
changeset 32692 8f60bd284bf4
parent 32534 b3ec7f3b3c2a
child 33414 2e284c36d51f
permissions -rw-r--r--
8055917: jdk.nashorn.internal.codegen.CompilationPhase$N should be renamed to proper classes Reviewed-by: attila, hannesw
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     1
/*
16151
97c1e756ae1e 8005663: Update copyright year to 2013
jlaskey
parents: 16147
diff changeset
     2
 * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     4
 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     7
 * published by the Free Software Foundation.  Oracle designates this
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
     9
 * by Oracle in the LICENSE file that accompanied this code.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    10
 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    15
 * accompanied this code).
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    16
 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    20
 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    23
 * questions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    24
 */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    25
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    26
package jdk.nashorn.internal.parser;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    27
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    28
import static jdk.nashorn.internal.codegen.CompilerConstants.ANON_FUNCTION_PREFIX;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    29
import static jdk.nashorn.internal.codegen.CompilerConstants.EVAL;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    30
import static jdk.nashorn.internal.codegen.CompilerConstants.PROGRAM;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    31
import static jdk.nashorn.internal.parser.TokenType.ASSIGN;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    32
import static jdk.nashorn.internal.parser.TokenType.CASE;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    33
import static jdk.nashorn.internal.parser.TokenType.CATCH;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    34
import static jdk.nashorn.internal.parser.TokenType.COLON;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    35
import static jdk.nashorn.internal.parser.TokenType.COMMARIGHT;
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
    36
import static jdk.nashorn.internal.parser.TokenType.CONST;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    37
import static jdk.nashorn.internal.parser.TokenType.DECPOSTFIX;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    38
import static jdk.nashorn.internal.parser.TokenType.DECPREFIX;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    39
import static jdk.nashorn.internal.parser.TokenType.ELSE;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    40
import static jdk.nashorn.internal.parser.TokenType.EOF;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    41
import static jdk.nashorn.internal.parser.TokenType.EOL;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    42
import static jdk.nashorn.internal.parser.TokenType.FINALLY;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    43
import static jdk.nashorn.internal.parser.TokenType.FUNCTION;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    44
import static jdk.nashorn.internal.parser.TokenType.IDENT;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    45
import static jdk.nashorn.internal.parser.TokenType.IF;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    46
import static jdk.nashorn.internal.parser.TokenType.INCPOSTFIX;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    47
import static jdk.nashorn.internal.parser.TokenType.LBRACE;
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
    48
import static jdk.nashorn.internal.parser.TokenType.LET;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    49
import static jdk.nashorn.internal.parser.TokenType.LPAREN;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    50
import static jdk.nashorn.internal.parser.TokenType.RBRACE;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    51
import static jdk.nashorn.internal.parser.TokenType.RBRACKET;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    52
import static jdk.nashorn.internal.parser.TokenType.RPAREN;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    53
import static jdk.nashorn.internal.parser.TokenType.SEMICOLON;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    54
import static jdk.nashorn.internal.parser.TokenType.TERNARY;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    55
import static jdk.nashorn.internal.parser.TokenType.WHILE;
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
    56
26646
332e9901f0ed 8058304: Non-serializable fields in serializable classes
hannesw
parents: 26505
diff changeset
    57
import java.io.Serializable;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    58
import java.util.ArrayDeque;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    59
import java.util.ArrayList;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    60
import java.util.Collections;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    61
import java.util.Deque;
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
    62
import java.util.HashMap;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    63
import java.util.HashSet;
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
    64
import java.util.Iterator;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    65
import java.util.List;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    66
import java.util.Map;
20213
414e257bb93e 8025080: Object literal getter, setter function with number format property name results in ClassFormatError
sundar
parents: 19898
diff changeset
    67
import jdk.internal.dynalink.support.NameCodec;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
    68
import jdk.nashorn.internal.codegen.CompilerConstants;
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
    69
import jdk.nashorn.internal.codegen.Namespace;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    70
import jdk.nashorn.internal.ir.AccessNode;
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
    71
import jdk.nashorn.internal.ir.BaseNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    72
import jdk.nashorn.internal.ir.BinaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    73
import jdk.nashorn.internal.ir.Block;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    74
import jdk.nashorn.internal.ir.BlockStatement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    75
import jdk.nashorn.internal.ir.BreakNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    76
import jdk.nashorn.internal.ir.CallNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    77
import jdk.nashorn.internal.ir.CaseNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    78
import jdk.nashorn.internal.ir.CatchNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    79
import jdk.nashorn.internal.ir.ContinueNode;
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
    80
import jdk.nashorn.internal.ir.DebuggerNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    81
import jdk.nashorn.internal.ir.EmptyNode;
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
    82
import jdk.nashorn.internal.ir.ErrorNode;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    83
import jdk.nashorn.internal.ir.Expression;
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    84
import jdk.nashorn.internal.ir.ExpressionStatement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    85
import jdk.nashorn.internal.ir.ForNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    86
import jdk.nashorn.internal.ir.FunctionNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    87
import jdk.nashorn.internal.ir.IdentNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    88
import jdk.nashorn.internal.ir.IfNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    89
import jdk.nashorn.internal.ir.IndexNode;
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
    90
import jdk.nashorn.internal.ir.JoinPredecessorExpression;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    91
import jdk.nashorn.internal.ir.LabelNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    92
import jdk.nashorn.internal.ir.LiteralNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    93
import jdk.nashorn.internal.ir.Node;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    94
import jdk.nashorn.internal.ir.ObjectNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    95
import jdk.nashorn.internal.ir.PropertyKey;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    96
import jdk.nashorn.internal.ir.PropertyNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    97
import jdk.nashorn.internal.ir.ReturnNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    98
import jdk.nashorn.internal.ir.RuntimeNode;
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
    99
import jdk.nashorn.internal.ir.Statement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   100
import jdk.nashorn.internal.ir.SwitchNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   101
import jdk.nashorn.internal.ir.TernaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   102
import jdk.nashorn.internal.ir.ThrowNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   103
import jdk.nashorn.internal.ir.TryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   104
import jdk.nashorn.internal.ir.UnaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   105
import jdk.nashorn.internal.ir.VarNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   106
import jdk.nashorn.internal.ir.WhileNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   107
import jdk.nashorn.internal.ir.WithNode;
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   108
import jdk.nashorn.internal.ir.debug.ASTWriter;
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   109
import jdk.nashorn.internal.ir.debug.PrintVisitor;
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   110
import jdk.nashorn.internal.runtime.Context;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   111
import jdk.nashorn.internal.runtime.ErrorManager;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   112
import jdk.nashorn.internal.runtime.JSErrorType;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   113
import jdk.nashorn.internal.runtime.ParserException;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   114
import jdk.nashorn.internal.runtime.RecompilableScriptFunctionData;
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   115
import jdk.nashorn.internal.runtime.ScriptEnvironment;
16245
6a1c6c8bc113 8008371: Fix Dynalink compiler warnings and whitespace
attila
parents: 16239
diff changeset
   116
import jdk.nashorn.internal.runtime.ScriptingFunctions;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   117
import jdk.nashorn.internal.runtime.Source;
26246
66c7c54fe70c 8055923: collect timings using System.nanoTime
attila
parents: 26243
diff changeset
   118
import jdk.nashorn.internal.runtime.Timing;
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   119
import jdk.nashorn.internal.runtime.logging.DebugLogger;
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   120
import jdk.nashorn.internal.runtime.logging.Loggable;
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   121
import jdk.nashorn.internal.runtime.logging.Logger;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   122
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   123
/**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   124
 * Builds the IR.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   125
 */
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   126
@Logger(name="parser")
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   127
public class Parser extends AbstractParser implements Loggable {
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   128
    private static final String ARGUMENTS_NAME = CompilerConstants.ARGUMENTS_VAR.symbolName();
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   129
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   130
    /** Current env. */
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   131
    private final ScriptEnvironment env;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   132
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
   133
    /** Is scripting mode. */
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
   134
    private final boolean scripting;
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
   135
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
   136
    private List<Statement> functionDeclarations;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   137
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   138
    private final ParserContext lc;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   139
    private final Deque<Object> defaultNames;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   140
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   141
    /** Namespace for function names where not explicitly given */
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   142
    private final Namespace namespace;
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   143
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   144
    private final DebugLogger log;
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
   145
18870
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   146
    /** to receive line information from Lexer when scanning multine literals. */
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   147
    protected final Lexer.LineInfoReceiver lineInfoReceiver;
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   148
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   149
    private RecompilableScriptFunctionData reparsedFunction;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   150
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   151
    /**
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   152
     * Constructor
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   153
     *
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   154
     * @param env     script environment
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   155
     * @param source  source to parse
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   156
     * @param errors  error manager
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   157
     */
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   158
    public Parser(final ScriptEnvironment env, final Source source, final ErrorManager errors) {
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   159
        this(env, source, errors, env._strict, null);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   160
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   161
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   162
    /**
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   163
     * Constructor
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   164
     *
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   165
     * @param env     script environment
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   166
     * @param source  source to parse
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   167
     * @param errors  error manager
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   168
     * @param strict  strict
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   169
     * @param log debug logger if one is needed
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   170
     */
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   171
    public Parser(final ScriptEnvironment env, final Source source, final ErrorManager errors, final boolean strict, final DebugLogger log) {
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   172
        this(env, source, errors, strict, 0, log);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   173
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   174
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   175
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   176
     * Construct a parser.
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   177
     *
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   178
     * @param env     script environment
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   179
     * @param source  source to parse
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   180
     * @param errors  error manager
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   181
     * @param strict  parser created with strict mode enabled.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   182
     * @param lineOffset line offset to start counting lines from
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   183
     * @param log debug logger if one is needed
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   184
     */
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   185
    public Parser(final ScriptEnvironment env, final Source source, final ErrorManager errors, final boolean strict, final int lineOffset, final DebugLogger log) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   186
        super(source, errors, strict, lineOffset);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   187
        this.lc = new ParserContext();
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   188
        this.defaultNames = new ArrayDeque<>();
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   189
        this.env = env;
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   190
        this.namespace = new Namespace(env.getNamespace());
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   191
        this.scripting = env._scripting;
18870
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   192
        if (this.scripting) {
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   193
            this.lineInfoReceiver = new Lexer.LineInfoReceiver() {
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   194
                @Override
19472
9476460521b3 8023017: SUB missing for widest op == number for BinaryNode
lagergren
parents: 18877
diff changeset
   195
                public void lineInfo(final int receiverLine, final int receiverLinePosition) {
18870
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   196
                    // update the parser maintained line information
19472
9476460521b3 8023017: SUB missing for widest op == number for BinaryNode
lagergren
parents: 18877
diff changeset
   197
                    Parser.this.line = receiverLine;
9476460521b3 8023017: SUB missing for widest op == number for BinaryNode
lagergren
parents: 18877
diff changeset
   198
                    Parser.this.linePosition = receiverLinePosition;
18870
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   199
                }
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   200
            };
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   201
        } else {
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   202
            // non-scripting mode script can't have multi-line literals
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   203
            this.lineInfoReceiver = null;
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
   204
        }
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   205
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   206
        this.log = log == null ? DebugLogger.DISABLED_LOGGER : log;
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   207
    }
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   208
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   209
    @Override
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   210
    public DebugLogger getLogger() {
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   211
        return log;
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   212
    }
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   213
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   214
    @Override
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   215
    public DebugLogger initLogger(final Context context) {
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   216
        return context.getLogger(this.getClass());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   217
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   218
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   219
    /**
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   220
     * Sets the name for the first function. This is only used when reparsing anonymous functions to ensure they can
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   221
     * preserve their already assigned name, as that name doesn't appear in their source text.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   222
     * @param name the name for the first parsed function.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   223
     */
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   224
    public void setFunctionName(final String name) {
26243
438aba09d465 8055911: Don't use String.intern for IdentNode
attila
parents: 26068
diff changeset
   225
        defaultNames.push(createIdentNode(0, 0, name));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   226
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   227
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   228
    /**
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   229
     * Sets the {@link RecompilableScriptFunctionData} representing the function being reparsed (when this
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   230
     * parser instance is used to reparse a previously parsed function, as part of its on-demand compilation).
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   231
     * This will trigger various special behaviors, such as skipping nested function bodies.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   232
     * @param reparsedFunction the function being reparsed.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   233
     */
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   234
    public void setReparsedFunction(final RecompilableScriptFunctionData reparsedFunction) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   235
        this.reparsedFunction = reparsedFunction;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   236
    }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   237
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
   238
    /**
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   239
     * Execute parse and return the resulting function node.
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   240
     * Errors will be thrown and the error manager will contain information
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   241
     * if parsing should fail
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   242
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   243
     * This is the default parse call, which will name the function node
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   244
     * {code :program} {@link CompilerConstants#PROGRAM}
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   245
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   246
     * @return function node resulting from successful parse
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   247
     */
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   248
    public FunctionNode parse() {
24759
31aed7d9c02a 8034206: Make parts of code pipeline reusable in order to facilitate faster warmup and faster lazy compilation.
lagergren
parents: 24751
diff changeset
   249
        return parse(PROGRAM.symbolName(), 0, source.getLength(), false);
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   250
    }
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   251
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   252
    /**
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   253
     * Execute parse and return the resulting function node.
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   254
     * Errors will be thrown and the error manager will contain information
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   255
     * if parsing should fail
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   256
     *
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   257
     * This should be used to create one and only one function node
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   258
     *
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   259
     * @param scriptName name for the script, given to the parsed FunctionNode
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   260
     * @param startPos start position in source
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   261
     * @param len length of parse
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   262
     * @param allowPropertyFunction if true, "get" and "set" are allowed as first tokens of the program, followed by
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   263
     * a property getter or setter function. This is used when reparsing a function that can potentially be defined as a
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   264
     * property getter or setter in an object literal.
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   265
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   266
     * @return function node resulting from successful parse
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   267
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   268
    public FunctionNode parse(final String scriptName, final int startPos, final int len, final boolean allowPropertyFunction) {
24764
722a9603b237 8043633: In order to remove global state outside of contexts, make sure Timing class is an instance and not a static global collection of data. Move into Context. Move -Dnashorn.timing to an official logging option.
lagergren
parents: 24759
diff changeset
   269
        final boolean isTimingEnabled = env.isTimingEnabled();
26246
66c7c54fe70c 8055923: collect timings using System.nanoTime
attila
parents: 26243
diff changeset
   270
        final long t0 = isTimingEnabled ? System.nanoTime() : 0L;
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   271
        log.info(this, " begin for '", scriptName, "'");
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
   272
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   273
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   274
            stream = new TokenStream();
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
   275
            lexer  = new Lexer(source, startPos, len, stream, scripting && !env._no_syntax_extensions, env._es6, reparsedFunction != null);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   276
            lexer.line = lexer.pendingLine = lineOffset + 1;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   277
            line = lineOffset;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   278
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   279
            // Set up first token (skips opening EOL.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   280
            k = -1;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   281
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   282
            // Begin parse.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   283
            return program(scriptName, allowPropertyFunction);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   284
        } catch (final Exception e) {
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   285
            handleParseException(e);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   286
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   287
            return null;
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   288
        } finally {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   289
            final String end = this + " end '" + scriptName + "'";
24764
722a9603b237 8043633: In order to remove global state outside of contexts, make sure Timing class is an instance and not a static global collection of data. Move into Context. Move -Dnashorn.timing to an official logging option.
lagergren
parents: 24759
diff changeset
   290
            if (isTimingEnabled) {
26246
66c7c54fe70c 8055923: collect timings using System.nanoTime
attila
parents: 26243
diff changeset
   291
                env._timing.accumulateTime(toString(), System.nanoTime() - t0);
66c7c54fe70c 8055923: collect timings using System.nanoTime
attila
parents: 26243
diff changeset
   292
                log.info(end, "' in ", Timing.toMillisPrint(System.nanoTime() - t0), " ms");
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   293
            } else {
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   294
                log.info(end);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   295
            }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   296
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   297
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   298
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   299
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   300
     * Parse and return the list of function parameter list. A comma
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   301
     * separated list of function parameter identifiers is expected to be parsed.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   302
     * Errors will be thrown and the error manager will contain information
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   303
     * if parsing should fail. This method is used to check if parameter Strings
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   304
     * passed to "Function" constructor is a valid or not.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   305
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   306
     * @return the list of IdentNodes representing the formal parameter list
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   307
     */
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   308
    public List<IdentNode> parseFormalParameterList() {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   309
        try {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   310
            stream = new TokenStream();
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
   311
            lexer  = new Lexer(source, stream, scripting && !env._no_syntax_extensions, env._es6);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   312
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   313
            // Set up first token (skips opening EOL.)
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   314
            k = -1;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   315
            next();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   316
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   317
            return formalParameterList(TokenType.EOF);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   318
        } catch (final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   319
            handleParseException(e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   320
            return null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   321
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   322
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   323
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   324
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   325
     * Execute parse and return the resulting function node.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   326
     * Errors will be thrown and the error manager will contain information
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   327
     * if parsing should fail. This method is used to check if code String
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   328
     * passed to "Function" constructor is a valid function body or not.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   329
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   330
     * @return function node resulting from successful parse
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   331
     */
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   332
    public FunctionNode parseFunctionBody() {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   333
        try {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   334
            stream = new TokenStream();
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
   335
            lexer  = new Lexer(source, stream, scripting && !env._no_syntax_extensions, env._es6);
24725
7bb1f687a852 8033334: Make sure that scope depth information is maintained in the RecompilableScriptFunctionDatas, to avoid unnecessary slow proto linkage when doing on demand compilation
lagergren
parents: 24719
diff changeset
   336
            final int functionLine = line;
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   337
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   338
            // Set up first token (skips opening EOL.)
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   339
            k = -1;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   340
            next();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   341
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   342
            // Make a fake token for the function.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   343
            final long functionToken = Token.toDesc(FUNCTION, 0, source.getLength());
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   344
            // Set up the function to append elements.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   345
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   346
            final IdentNode ident = new IdentNode(functionToken, Token.descPosition(functionToken), PROGRAM.symbolName());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   347
            final ParserContextFunctionNode function = createParserContextFunctionNode(ident, functionToken, FunctionNode.Kind.NORMAL, functionLine, Collections.<IdentNode>emptyList());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   348
            lc.push(function);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   349
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   350
            final ParserContextBlockNode body = newBlock();
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   351
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   352
            functionDeclarations = new ArrayList<>();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   353
            sourceElements(false);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   354
            addFunctionDeclarations(function);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   355
            functionDeclarations = null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   356
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   357
            restoreBlock(body);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   358
            body.setFlag(Block.NEEDS_SCOPE);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   359
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   360
            final Block functionBody = new Block(functionToken, source.getLength() - 1,
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   361
                body.getFlags() | Block.IS_SYNTHETIC, body.getStatements());
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   362
            lc.pop(function);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   363
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   364
            expect(EOF);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   365
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   366
            final FunctionNode functionNode = createFunctionNode(
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   367
                    function,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   368
                    functionToken,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   369
                    ident,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   370
                    Collections.<IdentNode>emptyList(),
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   371
                    FunctionNode.Kind.NORMAL,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   372
                    functionLine,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   373
                    functionBody);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   374
            printAST(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   375
            return functionNode;
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   376
        } catch (final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   377
            handleParseException(e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   378
            return null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   379
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   380
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   381
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   382
    private void handleParseException(final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   383
        // Extract message from exception.  The message will be in error
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   384
        // message format.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   385
        String message = e.getMessage();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   386
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   387
        // If empty message.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   388
        if (message == null) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   389
            message = e.toString();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   390
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   391
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   392
        // Issue message.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   393
        if (e instanceof ParserException) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   394
            errors.error((ParserException)e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   395
        } else {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   396
            errors.error(message);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   397
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   398
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   399
        if (env._dump_on_error) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   400
            e.printStackTrace(env.getErr());
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   401
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   402
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   403
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   404
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   405
     * Skip to a good parsing recovery point.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   406
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   407
    private void recover(final Exception e) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   408
        if (e != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   409
            // Extract message from exception.  The message will be in error
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   410
            // message format.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   411
            String message = e.getMessage();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   412
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   413
            // If empty message.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   414
            if (message == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   415
                message = e.toString();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   416
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   417
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   418
            // Issue message.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   419
            if (e instanceof ParserException) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   420
                errors.error((ParserException)e);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   421
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   422
                errors.error(message);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   423
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   424
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   425
            if (env._dump_on_error) {
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   426
                e.printStackTrace(env.getErr());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   427
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   428
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   429
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   430
        // Skip to a recovery point.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   431
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   432
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   433
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   434
            case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   435
                // Can not go any further.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   436
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   437
            case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   438
            case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   439
            case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   440
                // Good recovery points.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   441
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   442
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   443
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   444
                // So we can recover after EOL.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   445
                nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   446
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   447
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   448
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   449
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   450
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   451
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   452
     * Set up a new block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   453
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   454
     * @return New block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   455
     */
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   456
    private ParserContextBlockNode newBlock() {
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   457
        return lc.push(new ParserContextBlockNode(token));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   458
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   459
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   460
    private ParserContextFunctionNode createParserContextFunctionNode(final IdentNode ident, final long functionToken, final FunctionNode.Kind kind, final int functionLine, final List<IdentNode> parameters) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   461
        // Build function name.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   462
        final StringBuilder sb = new StringBuilder();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   463
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   464
        final ParserContextFunctionNode parentFunction = lc.getCurrentFunction();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   465
        if (parentFunction != null && !parentFunction.isProgram()) {
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   466
            sb.append(parentFunction.getName()).append('$');
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   467
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   468
22374
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   469
        assert ident.getName() != null;
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   470
        sb.append(ident.getName());
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   471
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   472
        final String name = namespace.uniqueName(sb.toString());
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   473
        assert parentFunction != null || name.equals(PROGRAM.symbolName()) || name.startsWith(RecompilableScriptFunctionData.RECOMPILATION_PREFIX) : "name = " + name;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   474
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   475
        int flags = 0;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   476
        if (isStrictMode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   477
            flags |= FunctionNode.IS_STRICT;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   478
        }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   479
        if (parentFunction == null) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   480
            flags |= FunctionNode.IS_PROGRAM;
17518
2225a4f929c0 8013477: Node.setSymbol needs to be copy on write - enable IR snapshots for recompilation based on callsite type specialization. [not enabled by default, hidden by a flag for now]
lagergren
parents: 17257
diff changeset
   481
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   482
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   483
        final ParserContextFunctionNode functionNode = new ParserContextFunctionNode(functionToken, ident, name, namespace, functionLine, kind, parameters);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   484
        functionNode.setFlag(flags);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   485
        return functionNode;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   486
    }
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   487
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   488
    private FunctionNode createFunctionNode(final ParserContextFunctionNode function, final long startToken, final IdentNode ident, final List<IdentNode> parameters, final FunctionNode.Kind kind, final int functionLine, final Block body){
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   489
        // Start new block.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   490
        final FunctionNode functionNode =
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   491
            new FunctionNode(
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   492
                source,
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   493
                functionLine,
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   494
                body.getToken(),
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   495
                Token.descPosition(body.getToken()),
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   496
                startToken,
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   497
                function.getLastToken(),
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   498
                namespace,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   499
                ident,
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   500
                function.getName(),
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   501
                parameters,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   502
                kind,
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   503
                function.getFlags(),
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   504
                body,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   505
                function.getEndParserState());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   506
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   507
        printAST(functionNode);
17518
2225a4f929c0 8013477: Node.setSymbol needs to be copy on write - enable IR snapshots for recompilation based on callsite type specialization. [not enabled by default, hidden by a flag for now]
lagergren
parents: 17257
diff changeset
   508
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   509
        return functionNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   510
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   511
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   512
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   513
     * Restore the current block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   514
     */
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   515
    private ParserContextBlockNode restoreBlock(final ParserContextBlockNode block) {
17518
2225a4f929c0 8013477: Node.setSymbol needs to be copy on write - enable IR snapshots for recompilation based on callsite type specialization. [not enabled by default, hidden by a flag for now]
lagergren
parents: 17257
diff changeset
   516
        return lc.pop(block);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   517
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   518
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   519
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   520
     * Get the statements in a block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   521
     * @return Block statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   522
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   523
    private Block getBlock(final boolean needsBraces) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   524
        final long blockToken = token;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   525
        final ParserContextBlockNode newBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   526
        try {
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   527
            // Block opening brace.
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   528
            if (needsBraces) {
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   529
                expect(LBRACE);
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   530
            }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   531
            // Accumulate block statements.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   532
            statementList();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   533
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   534
        } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   535
            restoreBlock(newBlock);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   536
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   537
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   538
        // Block closing brace.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   539
        if (needsBraces) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   540
            expect(RBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   541
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   542
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   543
        final int flags = newBlock.getFlags() | (needsBraces? 0 : Block.IS_SYNTHETIC);
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   544
        return new Block(blockToken, finish, flags, newBlock.getStatements());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   545
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   546
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   547
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   548
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   549
     * Get all the statements generated by a single statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   550
     * @return Statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   551
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   552
    private Block getStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   553
        if (type == LBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   554
            return getBlock(true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   555
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   556
        // Set up new block. Captures first token.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   557
        final ParserContextBlockNode newBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   558
        try {
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   559
            statement(false, false, true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   560
        } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   561
            restoreBlock(newBlock);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   562
        }
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   563
        return new Block(newBlock.getToken(), finish, newBlock.getFlags() | Block.IS_SYNTHETIC, newBlock.getStatements());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   564
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   565
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   566
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   567
     * Detect calls to special functions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   568
     * @param ident Called function.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   569
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   570
    private void detectSpecialFunction(final IdentNode ident) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   571
        final String name = ident.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   572
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   573
        if (EVAL.symbolName().equals(name)) {
17255
aa61d23e36e5 8013419: Streamline handling of with and eval
attila
parents: 17249
diff changeset
   574
            markEval(lc);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   575
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   576
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   577
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   578
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   579
     * Detect use of special properties.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   580
     * @param ident Referenced property.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   581
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   582
    private void detectSpecialProperty(final IdentNode ident) {
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   583
        if (isArguments(ident)) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   584
            lc.getCurrentFunction().setFlag(FunctionNode.USES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   585
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   586
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   587
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   588
    private boolean useBlockScope() {
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   589
        return env._es6;
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   590
    }
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   591
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   592
    private static boolean isArguments(final String name) {
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   593
        return ARGUMENTS_NAME.equals(name);
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   594
    }
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   595
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   596
    private static boolean isArguments(final IdentNode ident) {
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   597
        return isArguments(ident.getName());
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   598
    }
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   599
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   600
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   601
     * Tells whether a IdentNode can be used as L-value of an assignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   602
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   603
     * @param ident IdentNode to be checked
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   604
     * @return whether the ident can be used as L-value
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   605
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   606
    private static boolean checkIdentLValue(final IdentNode ident) {
30392
dc4a419b2982 8079362: Enforce best practices for Node token API usage
attila
parents: 29539
diff changeset
   607
        return ident.tokenType().getKind() != TokenKind.KEYWORD;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   608
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   609
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   610
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   611
     * Verify an assignment expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   612
     * @param op  Operation token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   613
     * @param lhs Left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   614
     * @param rhs Right hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   615
     * @return Verified expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   616
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   617
    private Expression verifyAssignment(final long op, final Expression lhs, final Expression rhs) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   618
        final TokenType opType = Token.descType(op);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   619
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   620
        switch (opType) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   621
        case ASSIGN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   622
        case ASSIGN_ADD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   623
        case ASSIGN_BIT_AND:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   624
        case ASSIGN_BIT_OR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   625
        case ASSIGN_BIT_XOR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   626
        case ASSIGN_DIV:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   627
        case ASSIGN_MOD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   628
        case ASSIGN_MUL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   629
        case ASSIGN_SAR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   630
        case ASSIGN_SHL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   631
        case ASSIGN_SHR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   632
        case ASSIGN_SUB:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   633
            if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   634
                  lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   635
                  lhs instanceof IdentNode)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
   636
                return referenceError(lhs, rhs, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   637
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   638
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   639
            if (lhs instanceof IdentNode) {
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
   640
                if (!checkIdentLValue((IdentNode)lhs)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
   641
                    return referenceError(lhs, rhs, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   642
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   643
                verifyStrictIdent((IdentNode)lhs, "assignment");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   644
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   645
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   646
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   647
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   648
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   649
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   650
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   651
        // Build up node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   652
        if(BinaryNode.isLogical(opType)) {
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   653
            return new BinaryNode(op, new JoinPredecessorExpression(lhs), new JoinPredecessorExpression(rhs));
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   654
        }
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   655
        return new BinaryNode(op, lhs, rhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   656
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   657
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   658
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   659
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   660
     * Reduce increment/decrement to simpler operations.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   661
     * @param firstToken First token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   662
     * @param tokenType  Operation token (INCPREFIX/DEC.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   663
     * @param expression Left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   664
     * @param isPostfix  Prefix or postfix.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   665
     * @return           Reduced expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   666
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   667
    private static UnaryNode incDecExpression(final long firstToken, final TokenType tokenType, final Expression expression, final boolean isPostfix) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   668
        if (isPostfix) {
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   669
            return new UnaryNode(Token.recast(firstToken, tokenType == DECPREFIX ? DECPOSTFIX : INCPOSTFIX), expression.getStart(), Token.descPosition(firstToken) + Token.descLength(firstToken), expression);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   670
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   671
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   672
        return new UnaryNode(firstToken, expression);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   673
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   674
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   675
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   676
     * -----------------------------------------------------------------------
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   677
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   678
     * Grammar based on
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   679
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   680
     *      ECMAScript Language Specification
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   681
     *      ECMA-262 5th Edition / December 2009
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   682
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   683
     * -----------------------------------------------------------------------
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   684
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   685
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   686
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   687
     * Program :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   688
     *      SourceElements?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   689
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   690
     * See 14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   691
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   692
     * Parse the top level script.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   693
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   694
    private FunctionNode program(final String scriptName, final boolean allowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   695
        // Make a pseudo-token for the script holding its start and length.
24994
92a19723a5ac 8047035: (function() "hello")() crashes in Lexer with jdk9
sundar
parents: 24769
diff changeset
   696
        final long functionToken = Token.toDesc(FUNCTION, Token.descPosition(Token.withDelimiter(token)), source.getLength());
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   697
        final int  functionLine  = line;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   698
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   699
        final IdentNode ident = new IdentNode(functionToken, Token.descPosition(functionToken), scriptName);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   700
        final ParserContextFunctionNode script = createParserContextFunctionNode(
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   701
                ident,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   702
                functionToken,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   703
                FunctionNode.Kind.SCRIPT,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   704
                functionLine,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   705
                Collections.<IdentNode>emptyList());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   706
        lc.push(script);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   707
        final ParserContextBlockNode body = newBlock();
27814
96427359f4fe 8057691: Nashorn: let & const declarations are not shared between scripts
hannesw
parents: 27102
diff changeset
   708
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   709
        functionDeclarations = new ArrayList<>();
27814
96427359f4fe 8057691: Nashorn: let & const declarations are not shared between scripts
hannesw
parents: 27102
diff changeset
   710
        sourceElements(allowPropertyFunction);
96427359f4fe 8057691: Nashorn: let & const declarations are not shared between scripts
hannesw
parents: 27102
diff changeset
   711
        addFunctionDeclarations(script);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   712
        functionDeclarations = null;
27814
96427359f4fe 8057691: Nashorn: let & const declarations are not shared between scripts
hannesw
parents: 27102
diff changeset
   713
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   714
        restoreBlock(body);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   715
        body.setFlag(Block.NEEDS_SCOPE);
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
   716
        final Block programBody = new Block(functionToken, finish, body.getFlags() | Block.IS_SYNTHETIC, body.getStatements());
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   717
        lc.pop(script);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   718
        script.setLastToken(token);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   719
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   720
        expect(EOF);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   721
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   722
        return createFunctionNode(script, functionToken, ident, Collections.<IdentNode>emptyList(), FunctionNode.Kind.SCRIPT, functionLine, programBody);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   723
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   724
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   725
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   726
     * Directive value or null if statement is not a directive.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   727
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   728
     * @param stmt Statement to be checked
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   729
     * @return Directive value if the given statement is a directive
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   730
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   731
    private String getDirective(final Node stmt) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   732
        if (stmt instanceof ExpressionStatement) {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   733
            final Node expr = ((ExpressionStatement)stmt).getExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   734
            if (expr instanceof LiteralNode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   735
                final LiteralNode<?> lit = (LiteralNode<?>)expr;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   736
                final long litToken = lit.getToken();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   737
                final TokenType tt = Token.descType(litToken);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   738
                // A directive is either a string or an escape string
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   739
                if (tt == TokenType.STRING || tt == TokenType.ESCSTRING) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   740
                    // Make sure that we don't unescape anything. Return as seen in source!
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   741
                    return source.getString(lit.getStart(), Token.descLength(litToken));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   742
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   743
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   744
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   745
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   746
        return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   747
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   748
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   749
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   750
     * SourceElements :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   751
     *      SourceElement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   752
     *      SourceElements SourceElement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   753
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   754
     * See 14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   755
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   756
     * Parse the elements of the script or function.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   757
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   758
    private void sourceElements(final boolean shouldAllowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   759
        List<Node>    directiveStmts        = null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   760
        boolean       checkDirective        = true;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   761
        boolean       allowPropertyFunction = shouldAllowPropertyFunction;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   762
        final boolean oldStrictMode         = isStrictMode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   763
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   764
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   765
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   766
            // If is a script, then process until the end of the script.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   767
            while (type != EOF) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   768
                // Break if the end of a code block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   769
                if (type == RBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   770
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   771
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   772
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   773
                try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   774
                    // Get the next element.
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   775
                    statement(true, allowPropertyFunction, false);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   776
                    allowPropertyFunction = false;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   777
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   778
                    // check for directive prologues
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   779
                    if (checkDirective) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   780
                        // skip any debug statement like line number to get actual first line
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   781
                        final Statement lastStatement = lc.getLastStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   782
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   783
                        // get directive prologue, if any
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   784
                        final String directive = getDirective(lastStatement);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   785
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   786
                        // If we have seen first non-directive statement,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   787
                        // no more directive statements!!
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   788
                        checkDirective = directive != null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   789
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   790
                        if (checkDirective) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   791
                            if (!oldStrictMode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   792
                                if (directiveStmts == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   793
                                    directiveStmts = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   794
                                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   795
                                directiveStmts.add(lastStatement);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   796
                            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   797
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   798
                            // handle use strict directive
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   799
                            if ("use strict".equals(directive)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   800
                                isStrictMode = true;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   801
                                final ParserContextFunctionNode function = lc.getCurrentFunction();
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   802
                                function.setFlag(FunctionNode.IS_STRICT);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   803
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   804
                                // We don't need to check these, if lexical environment is already strict
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   805
                                if (!oldStrictMode && directiveStmts != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   806
                                    // check that directives preceding this one do not violate strictness
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   807
                                    for (final Node statement : directiveStmts) {
32534
b3ec7f3b3c2a 8136349: Typos patch for nashorn sources submitted on Sep 10, 2015
sundar
parents: 32444
diff changeset
   808
                                        // the get value will force unescape of preceding
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   809
                                        // escaped string directives
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   810
                                        getValue(statement.getToken());
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   811
                                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   812
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   813
                                    // verify that function name as well as parameter names
16201
889ddb179cdf 8007062: Split Lower up into Lower/Attr/FinalizeTypes. Integrate AccessSpecalizer into FinalizeTypes.
lagergren
parents: 16196
diff changeset
   814
                                    // satisfy strict mode restrictions.
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   815
                                    verifyStrictIdent(function.getIdent(), "function name");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   816
                                    for (final IdentNode param : function.getParameters()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   817
                                        verifyStrictIdent(param, "function parameter");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   818
                                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   819
                                }
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   820
                            } else if (Context.DEBUG) {
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   821
                                final int flag = FunctionNode.getDirectiveFlag(directive);
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   822
                                if (flag != 0) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   823
                                    final ParserContextFunctionNode function = lc.getCurrentFunction();
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
   824
                                    function.setFlag(flag);
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   825
                                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   826
                            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   827
                        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   828
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   829
                } catch (final Exception e) {
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   830
                    final int errorLine = line;
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   831
                    final long errorToken = token;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   832
                    //recover parsing
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   833
                    recover(e);
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   834
                    final ErrorNode errorExpr = new ErrorNode(errorToken, finish);
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   835
                    final ExpressionStatement expressionStatement = new ExpressionStatement(errorLine, errorToken, finish, errorExpr);
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
   836
                    appendStatement(expressionStatement);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   837
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   838
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   839
                // No backtracking from here on.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   840
                stream.commit(k);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   841
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   842
        } finally {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   843
            isStrictMode = oldStrictMode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   844
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   845
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   846
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   847
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   848
     * Statement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   849
     *      Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   850
     *      VariableStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   851
     *      EmptyStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   852
     *      ExpressionStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   853
     *      IfStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   854
     *      IterationStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   855
     *      ContinueStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   856
     *      BreakStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   857
     *      ReturnStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   858
     *      WithStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   859
     *      LabelledStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   860
     *      SwitchStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   861
     *      ThrowStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   862
     *      TryStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   863
     *      DebuggerStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   864
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   865
     * see 12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   866
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   867
     * Parse any of the basic statement types.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   868
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   869
    private void statement() {
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   870
        statement(false, false, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   871
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   872
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   873
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   874
     * @param topLevel does this statement occur at the "top level" of a script or a function?
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   875
     * @param allowPropertyFunction allow property "get" and "set" functions?
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   876
     * @param singleStatement are we in a single statement context?
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   877
     */
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   878
    private void statement(final boolean topLevel, final boolean allowPropertyFunction, final boolean singleStatement) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   879
        if (type == FUNCTION) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   880
            // As per spec (ECMA section 12), function declarations as arbitrary statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   881
            // is not "portable". Implementation can issue a warning or disallow the same.
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   882
            functionExpression(true, topLevel);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   883
            return;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   884
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   885
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   886
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   887
        case LBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   888
            block();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   889
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   890
        case VAR:
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   891
            variableStatement(type, true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   892
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   893
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   894
            emptyStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   895
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   896
        case IF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   897
            ifStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   898
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   899
        case FOR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   900
            forStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   901
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   902
        case WHILE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   903
            whileStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   904
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   905
        case DO:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   906
            doStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   907
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   908
        case CONTINUE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   909
            continueStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   910
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   911
        case BREAK:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   912
            breakStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   913
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   914
        case RETURN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   915
            returnStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   916
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   917
        case YIELD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   918
            yieldStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   919
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   920
        case WITH:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   921
            withStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   922
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   923
        case SWITCH:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   924
            switchStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   925
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   926
        case THROW:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   927
            throwStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   928
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   929
        case TRY:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   930
            tryStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   931
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   932
        case DEBUGGER:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   933
            debuggerStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   934
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   935
        case RPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   936
        case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   937
        case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   938
            expect(SEMICOLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   939
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   940
        default:
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   941
            if (useBlockScope() && (type == LET || type == CONST)) {
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   942
                if (singleStatement) {
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   943
                    throw error(AbstractParser.message("expected.stmt", type.getName() + " declaration"), token);
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
   944
                }
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   945
                variableStatement(type, true);
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   946
                break;
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   947
            }
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   948
            if (env._const_as_var && type == CONST) {
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
   949
                variableStatement(TokenType.VAR, true);
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   950
                break;
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   951
            }
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   952
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   953
            if (type == IDENT || isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   954
                if (T(k + 1) == COLON) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   955
                    labelStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   956
                    return;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   957
                }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   958
                if(allowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   959
                    final String ident = (String)getValue();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   960
                    final long propertyToken = token;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   961
                    final int propertyLine = line;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   962
                    if("get".equals(ident)) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   963
                        next();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   964
                        addPropertyFunctionStatement(propertyGetterFunction(propertyToken, propertyLine));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   965
                        return;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   966
                    } else if("set".equals(ident)) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   967
                        next();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   968
                        addPropertyFunctionStatement(propertySetterFunction(propertyToken, propertyLine));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   969
                        return;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   970
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   971
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   972
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   973
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   974
            expressionStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   975
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   976
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   977
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   978
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   979
    private void addPropertyFunctionStatement(final PropertyFunction propertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   980
        final FunctionNode fn = propertyFunction.functionNode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   981
        functionDeclarations.add(new ExpressionStatement(fn.getLineNumber(), fn.getToken(), finish, fn));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   982
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   983
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   984
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   985
     * block :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   986
     *      { StatementList? }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   987
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   988
     * see 12.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   989
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   990
     * Parse a statement block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   991
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   992
    private void block() {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   993
        appendStatement(new BlockStatement(line, getBlock(true)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   994
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   995
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   996
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   997
     * StatementList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   998
     *      Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   999
     *      StatementList Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1000
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1001
     * See 12.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1002
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1003
     * Parse a list of statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1004
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1005
    private void statementList() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1006
        // Accumulate statements until end of list. */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1007
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1008
        while (type != EOF) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1009
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1010
            case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1011
            case CASE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1012
            case DEFAULT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1013
            case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1014
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1015
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1016
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1017
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1018
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1019
            // Get next statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1020
            statement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1021
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1022
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1023
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1024
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1025
     * Make sure that in strict mode, the identifier name used is allowed.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1026
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1027
     * @param ident         Identifier that is verified
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1028
     * @param contextString String used in error message to give context to the user
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1029
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1030
    private void verifyStrictIdent(final IdentNode ident, final String contextString) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1031
        if (isStrictMode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1032
            switch (ident.getName()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1033
            case "eval":
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1034
            case "arguments":
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1035
                throw error(AbstractParser.message("strict.name", ident.getName(), contextString), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1036
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1037
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1038
            }
20571
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1039
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1040
            if (ident.isFutureStrictName()) {
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1041
                throw error(AbstractParser.message("strict.name", ident.getName(), contextString), ident.getToken());
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1042
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1043
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1044
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1045
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1046
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1047
     * VariableStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1048
     *      var VariableDeclarationList ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1049
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1050
     * VariableDeclarationList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1051
     *      VariableDeclaration
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1052
     *      VariableDeclarationList , VariableDeclaration
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1053
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1054
     * VariableDeclaration :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1055
     *      Identifier Initializer?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1056
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1057
     * Initializer :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1058
     *      = AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1059
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1060
     * See 12.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1061
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1062
     * Parse a VAR statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1063
     * @param isStatement True if a statement (not used in a FOR.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1064
     */
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1065
    private List<VarNode> variableStatement(final TokenType varType, final boolean isStatement) {
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1066
        return variableStatement(varType, isStatement, -1);
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1067
    }
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1068
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1069
    private List<VarNode> variableStatement(final TokenType varType, final boolean isStatement, final int sourceOrder) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1070
        // VAR tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1071
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1072
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1073
        final List<VarNode> vars = new ArrayList<>();
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1074
        int varFlags = 0;
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1075
        if (varType == LET) {
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1076
            varFlags |= VarNode.IS_LET;
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1077
        } else if (varType == CONST) {
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1078
            varFlags |= VarNode.IS_CONST;
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1079
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1080
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1081
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1082
            // Get starting token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1083
            final int  varLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1084
            final long varToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1085
            // Get name of var.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1086
            final IdentNode name = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1087
            verifyStrictIdent(name, "variable name");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1088
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1089
            // Assume no init.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1090
            Expression init = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1091
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1092
            // Look for initializer assignment.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1093
            if (type == ASSIGN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1094
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1095
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1096
                // Get initializer expression. Suppress IN if not statement.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1097
                defaultNames.push(name);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1098
                try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1099
                    init = assignmentExpression(!isStatement);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1100
                } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1101
                    defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1102
                }
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1103
            } else if (varType == CONST) {
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1104
                throw error(AbstractParser.message("missing.const.assignment", name.getName()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1105
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1106
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1107
            // Allocate var node.
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1108
            final VarNode var = new VarNode(varLine, varToken, sourceOrder, finish, name.setIsDeclaredHere(), init, varFlags);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1109
            vars.add(var);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1110
            appendStatement(var);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1111
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1112
            if (type != COMMARIGHT) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1113
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1114
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1115
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1116
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1117
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1118
        // If is a statement then handle end of line.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1119
        if (isStatement) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1120
            endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1121
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1122
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1123
        return vars;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1124
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1125
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1126
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1127
     * EmptyStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1128
     *      ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1129
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1130
     * See 12.3
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1131
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1132
     * Parse an empty statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1133
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1134
    private void emptyStatement() {
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  1135
        if (env._empty_statements) {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1136
            appendStatement(new EmptyNode(line, token, Token.descPosition(token) + Token.descLength(token)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1137
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1138
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1139
        // SEMICOLON checked in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1140
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1141
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1142
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1143
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1144
     * ExpressionStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1145
     *      Expression ; // [lookahead ~( or  function )]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1146
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1147
     * See 12.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1148
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1149
     * Parse an expression used in a statement block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1150
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1151
    private void expressionStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1152
        // Lookahead checked in caller.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1153
        final int  expressionLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1154
        final long expressionToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1155
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1156
        // Get expression and add as statement.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1157
        final Expression expression = expression();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1158
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1159
        ExpressionStatement expressionStatement = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1160
        if (expression != null) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1161
            expressionStatement = new ExpressionStatement(expressionLine, expressionToken, finish, expression);
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1162
            appendStatement(expressionStatement);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1163
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1164
            expect(null);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1165
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1166
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1167
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1168
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1169
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1170
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1171
     * IfStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1172
     *      if ( Expression ) Statement else Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1173
     *      if ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1174
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1175
     * See 12.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1176
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1177
     * Parse an IF statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1178
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1179
    private void ifStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1180
        // Capture IF token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1181
        final int  ifLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1182
        final long ifToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1183
         // IF tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1184
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1185
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1186
        expect(LPAREN);
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1187
        final Expression test = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1188
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1189
        final Block pass = getStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1190
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1191
        Block fail = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1192
        if (type == ELSE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1193
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1194
            fail = getStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1195
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1196
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1197
        appendStatement(new IfNode(ifLine, ifToken, fail != null ? fail.getFinish() : pass.getFinish(), test, pass, fail));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1198
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1199
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1200
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1201
     * ... IterationStatement:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1202
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1203
     *           for ( Expression[NoIn]?; Expression? ; Expression? ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1204
     *           for ( var VariableDeclarationList[NoIn]; Expression? ; Expression? ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1205
     *           for ( LeftHandSideExpression in Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1206
     *           for ( var VariableDeclaration[NoIn] in Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1207
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1208
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1209
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1210
     * Parse a FOR statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1211
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1212
    private void forStatement() {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1213
        final long forToken = token;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1214
        final int forLine = line;
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1215
        // start position of this for statement. This is used
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1216
        // for sort order for variables declared in the initializer
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1217
        // part of this 'for' statement (if any).
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1218
        final int forStart = Token.descPosition(forToken);
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1219
        // When ES6 for-let is enabled we create a container block to capture the LET.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1220
        final ParserContextBlockNode outer = useBlockScope() ? newBlock() : null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1221
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1222
        // Create FOR node, capturing FOR token.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1223
        final ParserContextLoopNode forNode = new ParserContextLoopNode();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1224
        lc.push(forNode);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1225
        Block body = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1226
        List<VarNode> vars = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1227
        Expression init = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1228
        JoinPredecessorExpression test = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1229
        JoinPredecessorExpression modify = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1230
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1231
        int flags = 0;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1232
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1233
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1234
            // FOR tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1235
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1236
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1237
            // Nashorn extension: for each expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1238
            // iterate property values rather than property names.
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  1239
            if (!env._no_syntax_extensions && type == IDENT && "each".equals(getValue())) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1240
                flags |= ForNode.IS_FOR_EACH;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1241
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1242
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1243
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1244
            expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1245
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1246
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1247
            switch (type) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1248
            case VAR:
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1249
                // Var declaration captured in for outer block.
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1250
                vars = variableStatement(type, false, forStart);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1251
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1252
            case SEMICOLON:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1253
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1254
            default:
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1255
                if (useBlockScope() && (type == LET || type == CONST)) {
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1256
                    if (type == LET) {
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1257
                        flags |= ForNode.PER_ITERATION_SCOPE;
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1258
                    }
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1259
                    // LET/CONST declaration captured in container block created above.
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1260
                    vars = variableStatement(type, false, forStart);
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1261
                    break;
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1262
                }
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1263
                if (env._const_as_var && type == CONST) {
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1264
                    // Var declaration captured in for outer block.
29539
b2a8fb583979 8075448: nashorn parser API returns init variable tree object of a for loop after for loop statement tree object
sundar
parents: 29407
diff changeset
  1265
                    vars = variableStatement(TokenType.VAR, false, forStart);
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1266
                    break;
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1267
                }
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1268
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1269
                init = expression(unaryExpression(), COMMARIGHT.getPrecedence(), true);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1270
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1271
            }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1272
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1273
            switch (type) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1274
            case SEMICOLON:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1275
                // for (init; test; modify)
18843
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1276
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1277
                // for each (init; test; modify) is invalid
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1278
                if ((flags & ForNode.IS_FOR_EACH) != 0) {
18843
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1279
                    throw error(AbstractParser.message("for.each.without.in"), token);
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1280
                }
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1281
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1282
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1283
                if (type != SEMICOLON) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1284
                    test = joinPredecessorExpression();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1285
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1286
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1287
                if (type != RPAREN) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1288
                    modify = joinPredecessorExpression();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1289
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1290
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1291
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1292
            case IN:
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1293
                flags |= ForNode.IS_FOR_IN;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1294
                test = new JoinPredecessorExpression();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1295
                if (vars != null) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1296
                    // for (var i in obj)
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1297
                    if (vars.size() == 1) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1298
                        init = new IdentNode(vars.get(0).getName());
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1299
                    } else {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1300
                        // for (var i, j in obj) is invalid
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1301
                        throw error(AbstractParser.message("many.vars.in.for.in.loop"), vars.get(1).getToken());
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1302
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1303
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1304
                } else {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1305
                    // for (expr in obj)
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1306
                    assert init != null : "for..in init expression can not be null here";
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1307
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1308
                    // check if initial expression is a valid L-value
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1309
                    if (!(init instanceof AccessNode ||
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1310
                          init instanceof IndexNode ||
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1311
                          init instanceof IdentNode)) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1312
                        throw error(AbstractParser.message("not.lvalue.for.in.loop"), init.getToken());
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1313
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1314
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1315
                    if (init instanceof IdentNode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1316
                        if (!checkIdentLValue((IdentNode)init)) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1317
                            throw error(AbstractParser.message("not.lvalue.for.in.loop"), init.getToken());
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1318
                        }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1319
                        verifyStrictIdent((IdentNode)init, "for-in iterator");
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1320
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1321
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1322
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1323
                next();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1324
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1325
                // Get the collection expression.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1326
                modify = joinPredecessorExpression();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1327
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1328
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1329
            default:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1330
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1331
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1332
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1333
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1334
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1335
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1336
            // Set the for body.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1337
            body = getStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1338
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1339
            lc.pop(forNode);
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1340
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1341
            if (vars != null) {
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1342
                for (final VarNode var : vars) {
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1343
                    appendStatement(var);
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1344
                }
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1345
            }
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1346
            if (body != null) {
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1347
                appendStatement(new ForNode(forLine, forToken, body.getFinish(), body, (forNode.getFlags() | flags), init, test, modify));
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1348
            }
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1349
            if (outer != null) {
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1350
                restoreBlock(outer);
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1351
                if (body != null) {
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1352
                    appendStatement(new BlockStatement(forLine, new Block(
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1353
                                    outer.getToken(),
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1354
                                    body.getFinish(),
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1355
                                    outer.getStatements())));
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1356
                }
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  1357
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1358
        }
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1359
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1360
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1361
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1362
     * ...IterationStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1363
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1364
     *           while ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1365
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1366
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1367
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1368
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1369
     * Parse while statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1370
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1371
    private void whileStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1372
        // Capture WHILE token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1373
        final long whileToken = token;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1374
        final int whileLine = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1375
        // WHILE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1376
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1377
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1378
        final ParserContextLoopNode whileNode = new ParserContextLoopNode();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1379
        lc.push(whileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1380
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1381
        JoinPredecessorExpression test = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1382
        Block body = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1383
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1384
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1385
            expect(LPAREN);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1386
            test = joinPredecessorExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1387
            expect(RPAREN);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1388
            body = getStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1389
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1390
            lc.pop(whileNode);
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1391
        }
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1392
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1393
        if (body != null) {
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1394
            appendStatement(new WhileNode(whileLine, whileToken, body.getFinish(), false, test, body));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1395
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1396
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1397
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1398
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1399
     * ...IterationStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1400
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1401
     *           do Statement while( Expression ) ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1402
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1403
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1404
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1405
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1406
     * Parse DO WHILE statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1407
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1408
    private void doStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1409
        // Capture DO token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1410
        final long doToken = token;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1411
        int doLine = 0;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1412
        // DO tested in the caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1413
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1414
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1415
        final ParserContextLoopNode doWhileNode = new ParserContextLoopNode();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1416
        lc.push(doWhileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1417
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1418
        Block body = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1419
        JoinPredecessorExpression test = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1420
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1421
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1422
           // Get DO body.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1423
            body = getStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1424
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1425
            expect(WHILE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1426
            expect(LPAREN);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1427
            doLine = line;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1428
            test = joinPredecessorExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1429
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1430
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1431
            if (type == SEMICOLON) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1432
                endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1433
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1434
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1435
            lc.pop(doWhileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1436
        }
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1437
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1438
        appendStatement(new WhileNode(doLine, doToken, finish, true, test, body));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1439
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1440
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1441
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1442
     * ContinueStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1443
     *      continue Identifier? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1444
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1445
     * See 12.7
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1446
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1447
     * Parse CONTINUE statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1448
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1449
    private void continueStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1450
        // Capture CONTINUE token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1451
        final int  continueLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1452
        final long continueToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1453
        // CONTINUE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1454
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1455
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1456
        ParserContextLabelNode labelNode = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1457
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1458
        // SEMICOLON or label.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1459
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1460
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1461
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1462
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1463
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1464
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1465
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1466
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1467
            final IdentNode ident = getIdent();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1468
            labelNode = lc.findLabel(ident.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1469
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1470
            if (labelNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1471
                throw error(AbstractParser.message("undefined.label", ident.getName()), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1472
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1473
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1474
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1475
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1476
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1477
        final String labelName = labelNode == null ? null : labelNode.getLabelName();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1478
        final ParserContextLoopNode targetNode = lc.getContinueTo(labelName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1479
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1480
        if (targetNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1481
            throw error(AbstractParser.message("illegal.continue.stmt"), continueToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1482
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1483
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1484
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1485
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1486
        // Construct and add CONTINUE node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1487
        appendStatement(new ContinueNode(continueLine, continueToken, finish, labelName));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1488
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1489
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1490
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1491
     * BreakStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1492
     *      break Identifier? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1493
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1494
     * See 12.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1495
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1496
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1497
    private void breakStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1498
        // Capture BREAK token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1499
        final int  breakLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1500
        final long breakToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1501
        // BREAK tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1502
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1503
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1504
        ParserContextLabelNode labelNode = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1505
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1506
        // SEMICOLON or label.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1507
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1508
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1509
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1510
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1511
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1512
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1513
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1514
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1515
            final IdentNode ident = getIdent();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1516
            labelNode = lc.findLabel(ident.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1517
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1518
            if (labelNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1519
                throw error(AbstractParser.message("undefined.label", ident.getName()), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1520
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1521
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1522
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1523
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1524
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1525
        //either an explicit label - then get its node or just a "break" - get first breakable
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1526
        //targetNode is what we are breaking out from.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1527
        final String labelName = labelNode == null ? null : labelNode.getLabelName();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1528
        final ParserContextBreakableNode targetNode = lc.getBreakable(labelName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1529
        if (targetNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1530
            throw error(AbstractParser.message("illegal.break.stmt"), breakToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1531
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1532
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1533
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1534
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1535
        // Construct and add BREAK node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1536
        appendStatement(new BreakNode(breakLine, breakToken, finish, labelName));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1537
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1538
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1539
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1540
     * ReturnStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1541
     *      return Expression? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1542
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1543
     * See 12.9
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1544
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1545
     * Parse RETURN statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1546
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1547
    private void returnStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1548
        // check for return outside function
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1549
        if (lc.getCurrentFunction().getKind() == FunctionNode.Kind.SCRIPT) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1550
            throw error(AbstractParser.message("invalid.return"));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1551
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1552
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1553
        // Capture RETURN token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1554
        final int  returnLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1555
        final long returnToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1556
        // RETURN tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1557
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1558
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1559
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1560
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1561
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1562
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1563
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1564
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1565
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1566
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1567
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1568
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1569
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1570
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1571
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1572
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1573
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1574
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1575
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1576
        // Construct and add RETURN node.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1577
        appendStatement(new ReturnNode(returnLine, returnToken, finish, expression));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1578
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1579
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1580
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1581
     * YieldStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1582
     *      yield Expression? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1583
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1584
     * JavaScript 1.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1585
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1586
     * Parse YIELD statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1587
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1588
    private void yieldStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1589
        // Capture YIELD token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1590
        final int  yieldLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1591
        final long yieldToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1592
        // YIELD tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1593
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1594
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1595
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1596
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1597
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1598
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1599
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1600
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1601
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1602
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1603
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1604
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1605
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1606
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1607
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1608
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1609
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1610
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1611
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1612
        // Construct and add YIELD node.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1613
        appendStatement(new ReturnNode(yieldLine, yieldToken, finish, expression));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1614
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1615
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1616
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1617
     * WithStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1618
     *      with ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1619
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1620
     * See 12.10
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1621
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1622
     * Parse WITH statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1623
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1624
    private void withStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1625
        // Capture WITH token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1626
        final int  withLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1627
        final long withToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1628
        // WITH tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1629
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1630
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1631
        // ECMA 12.10.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1632
        if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1633
            throw error(AbstractParser.message("strict.no.with"), withToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1634
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1635
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1636
        expect(LPAREN);
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1637
        final Expression expression = expression();
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1638
        expect(RPAREN);
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1639
        final Block body = getStatement();
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1640
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1641
        appendStatement(new WithNode(withLine, withToken, finish, expression, body));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1642
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1643
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1644
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1645
     * SwitchStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1646
     *      switch ( Expression ) CaseBlock
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1647
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1648
     * CaseBlock :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1649
     *      { CaseClauses? }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1650
     *      { CaseClauses? DefaultClause CaseClauses }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1651
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1652
     * CaseClauses :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1653
     *      CaseClause
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1654
     *      CaseClauses CaseClause
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1655
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1656
     * CaseClause :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1657
     *      case Expression : StatementList?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1658
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1659
     * DefaultClause :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1660
     *      default : StatementList?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1661
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1662
     * See 12.11
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1663
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1664
     * Parse SWITCH statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1665
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1666
    private void switchStatement() {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1667
        final int  switchLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1668
        final long switchToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1669
        // SWITCH tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1670
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1671
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1672
        // Create and add switch statement.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1673
        final ParserContextSwitchNode switchNode= new ParserContextSwitchNode();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1674
        lc.push(switchNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1675
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1676
        CaseNode defaultCase = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1677
        // Prepare to accumulate cases.
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1678
        final List<CaseNode> cases = new ArrayList<>();
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1679
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1680
        Expression expression = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1681
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1682
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1683
            expect(LPAREN);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1684
            expression = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1685
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1686
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1687
            expect(LBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1688
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1689
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1690
            while (type != RBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1691
                // Prepare for next case.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1692
                Expression caseExpression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1693
                final long caseToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1694
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1695
                switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1696
                case CASE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1697
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1698
                    caseExpression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1699
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1700
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1701
                case DEFAULT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1702
                    if (defaultCase != null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1703
                        throw error(AbstractParser.message("duplicate.default.in.switch"));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1704
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1705
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1706
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1707
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1708
                default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1709
                    // Force an error.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1710
                    expect(CASE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1711
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1712
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1713
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1714
                expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1715
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1716
                // Get CASE body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1717
                final Block statements = getBlock(false);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1718
                final CaseNode caseNode = new CaseNode(caseToken, finish, caseExpression, statements);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1719
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1720
                if (caseExpression == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1721
                    defaultCase = caseNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1722
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1723
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1724
                cases.add(caseNode);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1725
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1726
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1727
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1728
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1729
            lc.pop(switchNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1730
        }
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1731
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1732
        appendStatement(new SwitchNode(switchLine, switchToken, finish, expression, cases, defaultCase));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1733
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1734
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1735
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1736
     * LabelledStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1737
     *      Identifier : Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1738
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1739
     * See 12.12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1740
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1741
     * Parse label statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1742
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1743
    private void labelStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1744
        // Capture label token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1745
        final long labelToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1746
        // Get label ident.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1747
        final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1748
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1749
        expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1750
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1751
        if (lc.findLabel(ident.getName()) != null) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1752
            throw error(AbstractParser.message("duplicate.label", ident.getName()), labelToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1753
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1754
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1755
        final ParserContextLabelNode labelNode = new ParserContextLabelNode(ident.getName());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1756
        Block body = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1757
        try {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1758
            lc.push(labelNode);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1759
            body = getStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1760
        } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1761
            assert lc.peek() instanceof ParserContextLabelNode;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1762
            lc.pop(labelNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1763
        }
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1764
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  1765
        appendStatement(new LabelNode(line, labelToken, finish, ident.getName(), body));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1766
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1767
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  1768
    /**
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1769
     * ThrowStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1770
     *      throw Expression ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1771
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1772
     * See 12.13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1773
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1774
     * Parse throw statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1775
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1776
    private void throwStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1777
        // Capture THROW token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1778
        final int  throwLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1779
        final long throwToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1780
        // THROW tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1781
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1782
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1783
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1784
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1785
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1786
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1787
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1788
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1789
        case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1790
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1791
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1792
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1793
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1794
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1795
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1796
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1797
        if (expression == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1798
            throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1799
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1800
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1801
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1802
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1803
        appendStatement(new ThrowNode(throwLine, throwToken, finish, expression, false));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1804
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1805
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1806
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1807
     * TryStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1808
     *      try Block Catch
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1809
     *      try Block Finally
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1810
     *      try Block Catch Finally
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1811
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1812
     * Catch :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1813
     *      catch( Identifier if Expression ) Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1814
     *      catch( Identifier ) Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1815
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1816
     * Finally :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1817
     *      finally Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1818
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1819
     * See 12.14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1820
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1821
     * Parse TRY statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1822
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1823
    private void tryStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1824
        // Capture TRY token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1825
        final int  tryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1826
        final long tryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1827
        // TRY tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1828
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1829
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1830
        // Container block needed to act as target for labeled break statements
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1831
        final int startLine = line;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1832
        final ParserContextBlockNode outer = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1833
        // Create try.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1834
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1835
        try {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1836
            final Block       tryBody     = getBlock(true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1837
            final List<Block> catchBlocks = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1838
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1839
            while (type == CATCH) {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1840
                final int  catchLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1841
                final long catchToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1842
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1843
                expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1844
                final IdentNode exception = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1845
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1846
                // ECMA 12.4.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1847
                verifyStrictIdent(exception, "catch argument");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1848
23766
a3ef17770bab 8039047: Parser accepts conditional catch clauses even when --no-syntax-extensions / -nse option is passed
sundar
parents: 23372
diff changeset
  1849
                // Nashorn extension: catch clause can have optional
a3ef17770bab 8039047: Parser accepts conditional catch clauses even when --no-syntax-extensions / -nse option is passed
sundar
parents: 23372
diff changeset
  1850
                // condition. So, a single try can have more than one
a3ef17770bab 8039047: Parser accepts conditional catch clauses even when --no-syntax-extensions / -nse option is passed
sundar
parents: 23372
diff changeset
  1851
                // catch clause each with it's own condition.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1852
                final Expression ifExpression;
23766
a3ef17770bab 8039047: Parser accepts conditional catch clauses even when --no-syntax-extensions / -nse option is passed
sundar
parents: 23372
diff changeset
  1853
                if (!env._no_syntax_extensions && type == IF) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1854
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1855
                    // Get the exception condition.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1856
                    ifExpression = expression();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1857
                } else {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1858
                    ifExpression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1859
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1860
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1861
                expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1862
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1863
                final ParserContextBlockNode catchBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1864
                try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1865
                    // Get CATCH body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1866
                    final Block catchBody = getBlock(true);
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1867
                    final CatchNode catchNode = new CatchNode(catchLine, catchToken, finish, exception, ifExpression, catchBody, false);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1868
                    appendStatement(catchNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1869
                } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1870
                    restoreBlock(catchBlock);
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
  1871
                    catchBlocks.add(new Block(catchBlock.getToken(), finish, catchBlock.getFlags() | Block.IS_SYNTHETIC, catchBlock.getStatements()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1872
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1873
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1874
                // If unconditional catch then should to be the end.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1875
                if (ifExpression == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1876
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1877
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1878
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1879
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1880
            // Prepare to capture finally statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1881
            Block finallyStatements = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1882
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1883
            if (type == FINALLY) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1884
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1885
                finallyStatements = getBlock(true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1886
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1887
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1888
            // Need at least one catch or a finally.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1889
            if (catchBlocks.isEmpty() && finallyStatements == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1890
                throw error(AbstractParser.message("missing.catch.or.finally"), tryToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1891
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1892
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1893
            final TryNode tryNode = new TryNode(tryLine, tryToken, finish, tryBody, catchBlocks, finallyStatements);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1894
            // Add try.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1895
            assert lc.peek() == outer;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1896
            appendStatement(tryNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1897
        } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1898
            restoreBlock(outer);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1899
        }
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1900
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
  1901
        appendStatement(new BlockStatement(startLine, new Block(tryToken, finish, outer.getFlags() | Block.IS_SYNTHETIC, outer.getStatements())));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1902
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1903
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1904
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1905
     * DebuggerStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1906
     *      debugger ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1907
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1908
     * See 12.15
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1909
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1910
     * Parse debugger statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1911
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1912
    private void  debuggerStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1913
        // Capture DEBUGGER token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1914
        final int  debuggerLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1915
        final long debuggerToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1916
        // DEBUGGER tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1917
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1918
        endOfLine();
29407
3fd4ede1581e 8074671: Nashorn Parser API
sundar
parents: 27974
diff changeset
  1919
        appendStatement(new DebuggerNode(debuggerLine, debuggerToken, finish));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1920
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1921
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1922
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1923
     * PrimaryExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1924
     *      this
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1925
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1926
     *      Literal
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1927
     *      ArrayLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1928
     *      ObjectLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1929
     *      ( Expression )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1930
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1931
     *  See 11.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1932
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1933
     * Parse primary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1934
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1935
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1936
    @SuppressWarnings("fallthrough")
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1937
    private Expression primaryExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1938
        // Capture first token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1939
        final int  primaryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1940
        final long primaryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1941
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1942
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1943
        case THIS:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1944
            final String name = type.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1945
            next();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  1946
            lc.getCurrentFunction().setFlag(FunctionNode.USES_THIS);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1947
            return new IdentNode(primaryToken, finish, name);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1948
        case IDENT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1949
            final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1950
            if (ident == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1951
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1952
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1953
            detectSpecialProperty(ident);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1954
            return ident;
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  1955
        case OCTAL_LEGACY:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1956
            if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1957
               throw error(AbstractParser.message("strict.no.octal"), token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1958
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1959
        case STRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1960
        case ESCSTRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1961
        case DECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1962
        case HEXADECIMAL:
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  1963
        case OCTAL:
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  1964
        case BINARY_NUMBER:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1965
        case FLOATING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1966
        case REGEX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1967
        case XML:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1968
            return getLiteral();
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1969
        case EXECSTRING:
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  1970
            return execString(primaryLine, primaryToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1971
        case FALSE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1972
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1973
            return LiteralNode.newInstance(primaryToken, finish, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1974
        case TRUE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1975
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1976
            return LiteralNode.newInstance(primaryToken, finish, true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1977
        case NULL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1978
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1979
            return LiteralNode.newInstance(primaryToken, finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1980
        case LBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1981
            return arrayLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1982
        case LBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1983
            return objectLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1984
        case LPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1985
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1986
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1987
            final Expression expression = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1988
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1989
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1990
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1991
            return expression;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1992
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1993
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1994
            // In this context some operator tokens mark the start of a literal.
18870
aa4fceda2fba 8020437: Wrong handling of line numbers with multiline string literals
sundar
parents: 18867
diff changeset
  1995
            if (lexer.scanLiteral(primaryToken, type, lineInfoReceiver)) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1996
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1997
                return getLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1998
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1999
            if (isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2000
                return getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2001
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2002
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2003
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2004
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2005
        return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2006
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2007
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2008
    /**
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2009
     * Convert execString to a call to $EXEC.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2010
     *
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2011
     * @param primaryToken Original string token.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2012
     * @return callNode to $EXEC.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2013
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2014
    CallNode execString(final int primaryLine, final long primaryToken) {
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2015
        // Synthesize an ident to call $EXEC.
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2016
        final IdentNode execIdent = new IdentNode(primaryToken, finish, ScriptingFunctions.EXEC_NAME);
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2017
        // Skip over EXECSTRING.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2018
        next();
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2019
        // Set up argument list for call.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2020
        // Skip beginning of edit string expression.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2021
        expect(LBRACE);
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2022
        // Add the following expression to arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2023
        final List<Expression> arguments = Collections.singletonList(expression());
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2024
        // Skip ending of edit string expression.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2025
        expect(RBRACE);
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2026
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2027
        return new CallNode(primaryLine, primaryToken, finish, execIdent, arguments, false);
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  2028
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2029
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2030
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2031
     * ArrayLiteral :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2032
     *      [ Elision? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2033
     *      [ ElementList ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2034
     *      [ ElementList , Elision? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2035
     *      [ expression for (LeftHandExpression in expression) ( (if ( Expression ) )? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2036
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2037
     * ElementList : Elision? AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2038
     *      ElementList , Elision? AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2039
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2040
     * Elision :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2041
     *      ,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2042
     *      Elision ,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2043
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2044
     * See 12.1.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2045
     * JavaScript 1.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2046
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2047
     * Parse array literal.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2048
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2049
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2050
    private LiteralNode<Expression[]> arrayLiteral() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2051
        // Capture LBRACKET token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2052
        final long arrayToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2053
        // LBRACKET tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2054
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2055
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2056
        // Prepare to accumulate elements.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2057
        final List<Expression> elements = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2058
        // Track elisions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2059
        boolean elision = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2060
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2061
        while (true) {
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2062
            switch (type) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2063
            case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2064
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2065
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2066
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2067
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2068
            case COMMARIGHT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2069
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2070
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2071
                // If no prior expression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2072
                if (elision) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2073
                    elements.add(null);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2074
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2075
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2076
                elision = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2077
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2078
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2079
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2080
            default:
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2081
                if (!elision) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2082
                    throw error(AbstractParser.message("expected.comma", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2083
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2084
                // Add expression element.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2085
                final Expression expression = assignmentExpression(false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2086
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2087
                if (expression != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2088
                    elements.add(expression);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2089
                } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2090
                    expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2091
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2092
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2093
                elision = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2094
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2095
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2096
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2097
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2098
        return LiteralNode.newInstance(arrayToken, finish, elements);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2099
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2100
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2101
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2102
     * ObjectLiteral :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2103
     *      { }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2104
     *      { PropertyNameAndValueList } { PropertyNameAndValueList , }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2105
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2106
     * PropertyNameAndValueList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2107
     *      PropertyAssignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2108
     *      PropertyNameAndValueList , PropertyAssignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2109
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2110
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2111
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2112
     * Parse an object literal.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2113
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2114
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2115
    private ObjectNode objectLiteral() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2116
        // Capture LBRACE token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2117
        final long objectToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2118
        // LBRACE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2119
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2120
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2121
        // Object context.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2122
        // Prepare to accumulate elements.
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2123
        final List<PropertyNode> elements = new ArrayList<>();
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2124
        final Map<String, Integer> map = new HashMap<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2125
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2126
        // Create a block for the object literal.
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2127
        boolean commaSeen = true;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2128
loop:
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2129
        while (true) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2130
            switch (type) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2131
                case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2132
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2133
                    break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2134
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2135
                case COMMARIGHT:
18629
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2136
                    if (commaSeen) {
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2137
                        throw error(AbstractParser.message("expected.property.id", type.getNameOrType()));
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2138
                    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2139
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2140
                    commaSeen = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2141
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2142
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2143
                default:
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2144
                    if (!commaSeen) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2145
                        throw error(AbstractParser.message("expected.comma", type.getNameOrType()));
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2146
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2147
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2148
                    commaSeen = false;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2149
                    // Get and add the next property.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2150
                    final PropertyNode property = propertyAssignment();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2151
                    final String key = property.getKeyName();
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2152
                    final Integer existing = map.get(key);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2153
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2154
                    if (existing == null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2155
                        map.put(key, elements.size());
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2156
                        elements.add(property);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2157
                        break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2158
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2159
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2160
                    final PropertyNode existingProperty = elements.get(existing);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2161
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2162
                    // ECMA section 11.1.5 Object Initialiser
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2163
                    // point # 4 on property assignment production
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2164
                    final Expression   value  = property.getValue();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2165
                    final FunctionNode getter = property.getGetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2166
                    final FunctionNode setter = property.getSetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2167
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2168
                    final Expression   prevValue  = existingProperty.getValue();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2169
                    final FunctionNode prevGetter = existingProperty.getGetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2170
                    final FunctionNode prevSetter = existingProperty.getSetter();
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2171
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2172
                    // ECMA 11.1.5 strict mode restrictions
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2173
                    if (isStrictMode && value != null && prevValue != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2174
                        throw error(AbstractParser.message("property.redefinition", key), property.getToken());
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2175
                    }
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2176
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2177
                    final boolean isPrevAccessor = prevGetter != null || prevSetter != null;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2178
                    final boolean isAccessor     = getter != null     || setter != null;
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2179
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2180
                    // data property redefined as accessor property
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2181
                    if (prevValue != null && isAccessor) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2182
                        throw error(AbstractParser.message("property.redefinition", key), property.getToken());
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2183
                    }
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2184
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2185
                    // accessor property redefined as data
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2186
                    if (isPrevAccessor && value != null) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2187
                        throw error(AbstractParser.message("property.redefinition", key), property.getToken());
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2188
                    }
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2189
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2190
                    if (isAccessor && isPrevAccessor) {
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2191
                        if (getter != null && prevGetter != null ||
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2192
                                setter != null && prevSetter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2193
                            throw error(AbstractParser.message("property.redefinition", key), property.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2194
                        }
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2195
                    }
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2196
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2197
                    if (value != null) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2198
                        elements.add(property);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2199
                    } else if (getter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2200
                        elements.set(existing, existingProperty.setGetter(getter));
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2201
                    } else if (setter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2202
                        elements.set(existing, existingProperty.setSetter(setter));
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  2203
                    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2204
                    break;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2205
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2206
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2207
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2208
        return new ObjectNode(objectToken, finish, elements);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2209
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2210
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2211
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2212
     * PropertyName :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2213
     *      IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2214
     *      StringLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2215
     *      NumericLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2216
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2217
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2218
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2219
     * @return PropertyName node
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2220
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2221
    @SuppressWarnings("fallthrough")
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2222
    private PropertyKey propertyName() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2223
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2224
        case IDENT:
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2225
            return getIdent().setIsPropertyName();
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  2226
        case OCTAL_LEGACY:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2227
            if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2228
                throw error(AbstractParser.message("strict.no.octal"), token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2229
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2230
        case STRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2231
        case ESCSTRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2232
        case DECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2233
        case HEXADECIMAL:
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  2234
        case OCTAL:
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  2235
        case BINARY_NUMBER:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2236
        case FLOATING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2237
            return getLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2238
        default:
19883
aae0838ac6ee 8024255: When a keyword is used as object property name, the property can not be deleted
sundar
parents: 19472
diff changeset
  2239
            return getIdentifierName().setIsPropertyName();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2240
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2241
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2242
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2243
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2244
     * PropertyAssignment :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2245
     *      PropertyName : AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2246
     *      get PropertyName ( ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2247
     *      set PropertyName ( PropertySetParameterList ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2248
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2249
     * PropertySetParameterList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2250
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2251
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2252
     * PropertyName :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2253
     *      IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2254
     *      StringLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2255
     *      NumericLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2256
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2257
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2258
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2259
     * Parse an object literal property.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2260
     * @return Property or reference node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2261
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2262
    private PropertyNode propertyAssignment() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2263
        // Capture firstToken.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2264
        final long propertyToken = token;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2265
        final int  functionLine  = line;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2266
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2267
        PropertyKey propertyName;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2268
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2269
        if (type == IDENT) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2270
            // Get IDENT.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2271
            final String ident = (String)expectValue(IDENT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2272
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2273
            if (type != COLON) {
20938
e92d8249f60c 8026302: source representation of getter and setter methods is wrong
sundar
parents: 20934
diff changeset
  2274
                final long getSetToken = propertyToken;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2275
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2276
                switch (ident) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2277
                case "get":
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2278
                    final PropertyFunction getter = propertyGetterFunction(getSetToken, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2279
                    return new PropertyNode(propertyToken, finish, getter.ident, null, getter.functionNode, null);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2280
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2281
                case "set":
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2282
                    final PropertyFunction setter = propertySetterFunction(getSetToken, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2283
                    return new PropertyNode(propertyToken, finish, setter.ident, null, null, setter.functionNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2284
                default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2285
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2286
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2287
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2288
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2289
            propertyName = createIdentNode(propertyToken, finish, ident).setIsPropertyName();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2290
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2291
            propertyName = propertyName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2292
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2293
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2294
        expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2295
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2296
        defaultNames.push(propertyName);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2297
        try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2298
            return new PropertyNode(propertyToken, finish, propertyName, assignmentExpression(false), null, null);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2299
        } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2300
            defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2301
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2302
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2303
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2304
    private PropertyFunction propertyGetterFunction(final long getSetToken, final int functionLine) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2305
        final PropertyKey getIdent = propertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2306
        final String getterName = getIdent.getPropertyName();
26243
438aba09d465 8055911: Don't use String.intern for IdentNode
attila
parents: 26068
diff changeset
  2307
        final IdentNode getNameNode = createIdentNode(((Node)getIdent).getToken(), finish, NameCodec.encode("get " + getterName));
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2308
        expect(LPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2309
        expect(RPAREN);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2310
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2311
        final ParserContextFunctionNode functionNode = createParserContextFunctionNode(getNameNode, getSetToken, FunctionNode.Kind.GETTER, functionLine, Collections.<IdentNode>emptyList());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2312
        lc.push(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2313
27819
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2314
        Block functionBody;
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2315
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2316
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2317
        try {
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2318
            functionBody = functionBody(functionNode);
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2319
        } finally {
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2320
            lc.pop(functionNode);
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2321
        }
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2322
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2323
        final FunctionNode  function = createFunctionNode(
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2324
                functionNode,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2325
                getSetToken,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2326
                getNameNode,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2327
                Collections.<IdentNode>emptyList(),
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2328
                FunctionNode.Kind.GETTER,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2329
                functionLine,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2330
                functionBody);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2331
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2332
        return new PropertyFunction(getIdent, function);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2333
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2334
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2335
    private PropertyFunction propertySetterFunction(final long getSetToken, final int functionLine) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2336
        final PropertyKey setIdent = propertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2337
        final String setterName = setIdent.getPropertyName();
26243
438aba09d465 8055911: Don't use String.intern for IdentNode
attila
parents: 26068
diff changeset
  2338
        final IdentNode setNameNode = createIdentNode(((Node)setIdent).getToken(), finish, NameCodec.encode("set " + setterName));
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2339
        expect(LPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2340
        // be sloppy and allow missing setter parameter even though
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2341
        // spec does not permit it!
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2342
        final IdentNode argIdent;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2343
        if (type == IDENT || isNonStrictModeIdent()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2344
            argIdent = getIdent();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2345
            verifyStrictIdent(argIdent, "setter argument");
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2346
        } else {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2347
            argIdent = null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2348
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2349
        expect(RPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2350
        final List<IdentNode> parameters = new ArrayList<>();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2351
        if (argIdent != null) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2352
            parameters.add(argIdent);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2353
        }
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2354
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2355
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2356
        final ParserContextFunctionNode functionNode = createParserContextFunctionNode(setNameNode, getSetToken, FunctionNode.Kind.SETTER, functionLine, parameters);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2357
        lc.push(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2358
27819
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2359
        Block functionBody;
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2360
        try {
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2361
            functionBody = functionBody(functionNode);
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2362
        } finally {
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2363
            lc.pop(functionNode);
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2364
        }
74baae50e5cd 8066238: AssertionError in parser when syntax errors appeared in non finished Blocks
lagergren
parents: 27817
diff changeset
  2365
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2366
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2367
        final FunctionNode  function = createFunctionNode(
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2368
                functionNode,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2369
                getSetToken,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2370
                setNameNode,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2371
                parameters,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2372
                FunctionNode.Kind.SETTER,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2373
                functionLine,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2374
                functionBody);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2375
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2376
        return new PropertyFunction(setIdent, function);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2377
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2378
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2379
    private static class PropertyFunction {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2380
        final PropertyKey ident;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2381
        final FunctionNode functionNode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2382
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2383
        PropertyFunction(final PropertyKey ident, final FunctionNode function) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2384
            this.ident = ident;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2385
            this.functionNode = function;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2386
        }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2387
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2388
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2389
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2390
     * LeftHandSideExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2391
     *      NewExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2392
     *      CallExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2393
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2394
     * CallExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2395
     *      MemberExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2396
     *      CallExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2397
     *      CallExpression [ Expression ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2398
     *      CallExpression . IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2399
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2400
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2401
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2402
     * Parse left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2403
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2404
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2405
    private Expression leftHandSideExpression() {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  2406
        int  callLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2407
        long callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2408
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2409
        Expression lhs = memberExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2410
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2411
        if (type == LPAREN) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2412
            final List<Expression> arguments = optimizeList(argumentList());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2413
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2414
            // Catch special functions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2415
            if (lhs instanceof IdentNode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2416
                detectSpecialFunction((IdentNode)lhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2417
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2418
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2419
            lhs = new CallNode(callLine, callToken, finish, lhs, arguments, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2420
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2421
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2422
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2423
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2424
            // Capture token.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  2425
            callLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2426
            callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2427
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2428
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2429
            case LPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2430
                // Get NEW or FUNCTION arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2431
                final List<Expression> arguments = optimizeList(argumentList());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2432
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2433
                // Create call node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2434
                lhs = new CallNode(callLine, callToken, finish, lhs, arguments, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2435
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2436
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2437
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2438
            case LBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2439
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2440
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2441
                // Get array index.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2442
                final Expression rhs = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2443
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2444
                expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2445
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2446
                // Create indexing node.
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2447
                lhs = new IndexNode(callToken, finish, lhs, rhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2448
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2449
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2450
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2451
            case PERIOD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2452
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2453
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2454
                final IdentNode property = getIdentifierName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2455
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2456
                // Create property access node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2457
                lhs = new AccessNode(callToken, finish, lhs, property.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2458
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2459
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2460
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2461
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2462
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2463
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2464
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2465
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2466
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2467
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2468
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2469
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2470
     * NewExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2471
     *      MemberExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2472
     *      new NewExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2473
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2474
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2475
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2476
     * Parse new expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2477
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2478
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2479
    private Expression newExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2480
        final long newToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2481
        // NEW is tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2482
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2483
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2484
        // Get function base.
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  2485
        final int  callLine    = line;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2486
        final Expression constructor = memberExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2487
        if (constructor == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2488
            return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2489
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2490
        // Get arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2491
        ArrayList<Expression> arguments;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2492
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2493
        // Allow for missing arguments.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2494
        if (type == LPAREN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2495
            arguments = argumentList();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2496
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2497
            arguments = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2498
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2499
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2500
        // Nashorn extension: This is to support the following interface implementation
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2501
        // syntax:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2502
        //
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2503
        //     var r = new java.lang.Runnable() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2504
        //         run: function() { println("run"); }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2505
        //     };
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2506
        //
32534
b3ec7f3b3c2a 8136349: Typos patch for nashorn sources submitted on Sep 10, 2015
sundar
parents: 32444
diff changeset
  2507
        // The object literal following the "new Constructor()" expression
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2508
        // is passed as an additional (last) argument to the constructor.
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  2509
        if (!env._no_syntax_extensions && type == LBRACE) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2510
            arguments.add(objectLiteral());
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2511
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2512
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2513
        final CallNode callNode = new CallNode(callLine, constructor.getToken(), finish, constructor, optimizeList(arguments), true);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2514
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2515
        return new UnaryNode(newToken, callNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2516
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2517
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2518
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2519
     * MemberExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2520
     *      PrimaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2521
     *      FunctionExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2522
     *      MemberExpression [ Expression ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2523
     *      MemberExpression . IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2524
     *      new MemberExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2525
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2526
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2527
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2528
     * Parse member expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2529
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2530
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2531
    private Expression memberExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2532
        // Prepare to build operation.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2533
        Expression lhs;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2534
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2535
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2536
        case NEW:
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2537
            // Get new expression.
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2538
            lhs = newExpression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2539
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2540
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2541
        case FUNCTION:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2542
            // Get function expression.
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2543
            lhs = functionExpression(false, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2544
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2545
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2546
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2547
            // Get primary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2548
            lhs = primaryExpression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2549
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2550
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2551
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2552
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2553
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2554
            // Capture token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2555
            final long callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2556
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2557
            switch (type) {
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2558
            case LBRACKET: {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2559
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2560
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2561
                // Get array index.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2562
                final Expression index = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2563
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2564
                expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2565
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2566
                // Create indexing node.
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2567
                lhs = new IndexNode(callToken, finish, lhs, index);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2568
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2569
                break;
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2570
            }
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2571
            case PERIOD: {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2572
                if (lhs == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2573
                    throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2574
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2575
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2576
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2577
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2578
                final IdentNode property = getIdentifierName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2579
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2580
                // Create property access node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2581
                lhs = new AccessNode(callToken, finish, lhs, property.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2582
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2583
                break;
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  2584
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2585
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2586
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2587
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2588
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2589
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2590
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2591
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2592
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2593
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2594
     * Arguments :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2595
     *      ( )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2596
     *      ( ArgumentList )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2597
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2598
     * ArgumentList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2599
     *      AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2600
     *      ArgumentList , AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2601
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2602
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2603
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2604
     * Parse function call arguments.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2605
     * @return Argument list.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2606
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2607
    private ArrayList<Expression> argumentList() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2608
        // Prepare to accumulate list of arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2609
        final ArrayList<Expression> nodeList = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2610
        // LPAREN tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2611
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2612
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2613
        // Track commas.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2614
        boolean first = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2615
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2616
        while (type != RPAREN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2617
            // Comma prior to every argument except the first.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2618
            if (!first) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2619
                expect(COMMARIGHT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2620
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2621
                first = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2622
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2623
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2624
            // Get argument expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2625
            nodeList.add(assignmentExpression(false));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2626
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2627
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2628
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2629
        return nodeList;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2630
    }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2631
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
  2632
    private static <T> List<T> optimizeList(final ArrayList<T> list) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2633
        switch(list.size()) {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2634
            case 0: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2635
                return Collections.emptyList();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2636
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2637
            case 1: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2638
                return Collections.singletonList(list.get(0));
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2639
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2640
            default: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2641
                list.trimToSize();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2642
                return list;
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2643
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2644
        }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2645
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2646
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2647
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2648
     * FunctionDeclaration :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2649
     *      function Identifier ( FormalParameterList? ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2650
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2651
     * FunctionExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2652
     *      function Identifier? ( FormalParameterList? ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2653
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2654
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2655
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2656
     * Parse function declaration.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2657
     * @param isStatement True if for is a statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2658
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2659
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2660
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2661
    private Expression functionExpression(final boolean isStatement, final boolean topLevel) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2662
        final long functionToken = token;
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  2663
        final int  functionLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2664
        // FUNCTION is tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2665
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2666
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2667
        IdentNode name = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2668
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2669
        if (type == IDENT || isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2670
            name = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2671
            verifyStrictIdent(name, "function name");
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2672
        } else if (isStatement) {
31095
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2673
            // Nashorn extension: anonymous function statements.
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2674
            // Do not allow anonymous function statement if extensions
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2675
            // are now allowed. But if we are reparsing then anon function
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2676
            // statement is possible - because it was used as function
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2677
            // expression in surrounding code.
790fc3d576f9 8085802: Nashorn -nse option causes parse error on anonymous function definition
sundar
parents: 30392
diff changeset
  2678
            if (env._no_syntax_extensions && reparsedFunction == null) {
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2679
                expect(IDENT);
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2680
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2681
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2682
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2683
        // name is null, generate anonymous name
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2684
        boolean isAnonymous = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2685
        if (name == null) {
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2686
            final String tmpName = getDefaultValidFunctionName(functionLine, isStatement);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2687
            name = new IdentNode(functionToken, Token.descPosition(functionToken), tmpName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2688
            isAnonymous = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2689
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2690
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2691
        expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2692
        final List<IdentNode> parameters = formalParameterList();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2693
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2694
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2695
        final ParserContextFunctionNode functionNode = createParserContextFunctionNode(name, functionToken, FunctionNode.Kind.NORMAL, functionLine, parameters);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2696
        lc.push(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2697
        Block functionBody = null;
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2698
        // Hide the current default name across function boundaries. E.g. "x3 = function x1() { function() {}}"
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2699
        // If we didn't hide the current default name, then the innermost anonymous function would receive "x3".
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2700
        hideDefaultName();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2701
        try{
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2702
            functionBody = functionBody(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2703
        } finally {
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2704
            defaultNames.pop();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2705
            lc.pop(functionNode);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2706
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2707
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2708
        if (isStatement) {
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  2709
            if (topLevel || useBlockScope()) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2710
                functionNode.setFlag(FunctionNode.IS_DECLARED);
17257
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2711
            } else if (isStrictMode) {
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2712
                throw error(JSErrorType.SYNTAX_ERROR, AbstractParser.message("strict.no.func.decl.here"), functionToken);
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2713
            } else if (env._function_statement == ScriptEnvironment.FunctionStatementBehavior.ERROR) {
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2714
                throw error(JSErrorType.SYNTAX_ERROR, AbstractParser.message("no.func.decl.here"), functionToken);
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2715
            } else if (env._function_statement == ScriptEnvironment.FunctionStatementBehavior.WARNING) {
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2716
                warning(JSErrorType.SYNTAX_ERROR, AbstractParser.message("no.func.decl.here.warn"), functionToken);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2717
            }
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2718
            if (isArguments(name)) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2719
               lc.getCurrentFunction().setFlag(FunctionNode.DEFINES_ARGUMENTS);
16206
83069fa0935b 8006529: Methods always get callee - it should be conditional
attila
parents: 16201
diff changeset
  2720
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2721
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2722
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2723
        if (isAnonymous) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2724
            functionNode.setFlag(FunctionNode.IS_ANONYMOUS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2725
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2726
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2727
        final int arity = parameters.size();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2728
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2729
        final boolean strict = functionNode.isStrict();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2730
        if (arity > 1) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2731
            final HashSet<String> parametersSet = new HashSet<>(arity);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2732
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2733
            for (int i = arity - 1; i >= 0; i--) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2734
                final IdentNode parameter = parameters.get(i);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2735
                String parameterName = parameter.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2736
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2737
                if (isArguments(parameterName)) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2738
                    functionNode.setFlag(FunctionNode.DEFINES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2739
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2740
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2741
                if (parametersSet.contains(parameterName)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2742
                    // redefinition of parameter name
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2743
                    if (strict) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2744
                        throw error(AbstractParser.message("strict.param.redefinition", parameterName), parameter.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2745
                    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2746
                    // rename in non-strict mode
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2747
                    parameterName = functionNode.uniqueName(parameterName);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2748
                    final long parameterToken = parameter.getToken();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2749
                    parameters.set(i, new IdentNode(parameterToken, Token.descPosition(parameterToken), functionNode.uniqueName(parameterName)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2750
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2751
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2752
                parametersSet.add(parameterName);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2753
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2754
        } else if (arity == 1) {
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2755
            if (isArguments(parameters.get(0))) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2756
                functionNode.setFlag(FunctionNode.DEFINES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2757
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2758
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2759
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2760
        final FunctionNode function = createFunctionNode(
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2761
                functionNode,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2762
                functionToken,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2763
                name,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2764
                parameters,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2765
                FunctionNode.Kind.NORMAL,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2766
                functionLine,
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2767
                functionBody);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2768
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2769
        if (isStatement) {
31485
be1acaee8e9e 8114838: Anonymous functions escape to surrounding scope when defined under "with" statement
sundar
parents: 31095
diff changeset
  2770
            if (isAnonymous) {
be1acaee8e9e 8114838: Anonymous functions escape to surrounding scope when defined under "with" statement
sundar
parents: 31095
diff changeset
  2771
                appendStatement(new ExpressionStatement(functionLine, functionToken, finish, function));
be1acaee8e9e 8114838: Anonymous functions escape to surrounding scope when defined under "with" statement
sundar
parents: 31095
diff changeset
  2772
                return function;
be1acaee8e9e 8114838: Anonymous functions escape to surrounding scope when defined under "with" statement
sundar
parents: 31095
diff changeset
  2773
            }
be1acaee8e9e 8114838: Anonymous functions escape to surrounding scope when defined under "with" statement
sundar
parents: 31095
diff changeset
  2774
27817
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  2775
            // mark ES6 block functions as lexically scoped
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  2776
            final int     varFlags = (topLevel || !useBlockScope()) ? 0 : VarNode.IS_LET;
56f6161c3e55 8057980: let & const: remaining issues with lexical scoping
hannesw
parents: 27814
diff changeset
  2777
            final VarNode varNode  = new VarNode(functionLine, functionToken, finish, name, function, varFlags);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2778
            if (topLevel) {
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2779
                functionDeclarations.add(varNode);
26377
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  2780
            } else if (useBlockScope()) {
028dad61662f 8051889: Implement block scoping in symbol assignment and scope computation
hannesw
parents: 26246
diff changeset
  2781
                prependStatement(varNode); // Hoist to beginning of current block
16191
7dd981da8e11 8006755: Functions inside with statements dont get correct scope
sundar
parents: 16187
diff changeset
  2782
            } else {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2783
                appendStatement(varNode);
16191
7dd981da8e11 8006755: Functions inside with statements dont get correct scope
sundar
parents: 16187
diff changeset
  2784
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2785
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2786
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2787
        return function;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2788
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2789
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2790
    private String getDefaultValidFunctionName(final int functionLine, final boolean isStatement) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2791
        final String defaultFunctionName = getDefaultFunctionName();
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2792
        if (isValidIdentifier(defaultFunctionName)) {
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2793
            if (isStatement) {
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2794
                // The name will be used as the LHS of a symbol assignment. We add the anonymous function
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2795
                // prefix to ensure that it can't clash with another variable.
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2796
                return ANON_FUNCTION_PREFIX.symbolName() + defaultFunctionName;
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2797
            }
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2798
            return defaultFunctionName;
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2799
        }
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2800
        return ANON_FUNCTION_PREFIX.symbolName() + functionLine;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2801
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2802
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
  2803
    private static boolean isValidIdentifier(final String name) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2804
        if(name == null || name.isEmpty()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2805
            return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2806
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2807
        if(!Character.isJavaIdentifierStart(name.charAt(0))) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2808
            return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2809
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2810
        for(int i = 1; i < name.length(); ++i) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2811
            if(!Character.isJavaIdentifierPart(name.charAt(i))) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2812
                return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2813
            }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2814
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2815
        return true;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2816
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2817
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2818
    private String getDefaultFunctionName() {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2819
        if(!defaultNames.isEmpty()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2820
            final Object nameExpr = defaultNames.peek();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2821
            if(nameExpr instanceof PropertyKey) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2822
                markDefaultNameUsed();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2823
                return ((PropertyKey)nameExpr).getPropertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2824
            } else if(nameExpr instanceof AccessNode) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2825
                markDefaultNameUsed();
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2826
                return ((AccessNode)nameExpr).getProperty();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2827
            }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2828
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2829
        return null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2830
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2831
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2832
    private void markDefaultNameUsed() {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2833
        defaultNames.pop();
27974
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2834
        hideDefaultName();
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2835
    }
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2836
4eca5d2c0088 8066221: anonymous function statement name clashes with another symbol
attila
parents: 27819
diff changeset
  2837
    private void hideDefaultName() {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2838
        // Can be any value as long as getDefaultFunctionName doesn't recognize it as something it can extract a value
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2839
        // from. Can't be null
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2840
        defaultNames.push("");
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2841
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2842
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2843
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2844
     * FormalParameterList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2845
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2846
     *      FormalParameterList , Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2847
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2848
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2849
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2850
     * Parse function parameter list.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2851
     * @return List of parameter nodes.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2852
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2853
    private List<IdentNode> formalParameterList() {
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2854
        return formalParameterList(RPAREN);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2855
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2856
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2857
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2858
     * Same as the other method of the same name - except that the end
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2859
     * token type expected is passed as argument to this method.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2860
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2861
     * FormalParameterList :
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2862
     *      Identifier
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2863
     *      FormalParameterList , Identifier
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2864
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2865
     * See 13
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2866
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2867
     * Parse function parameter list.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2868
     * @return List of parameter nodes.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2869
     */
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2870
    private List<IdentNode> formalParameterList(final TokenType endType) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2871
        // Prepare to gather parameters.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2872
        final ArrayList<IdentNode> parameters = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2873
        // Track commas.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2874
        boolean first = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2875
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2876
        while (type != endType) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2877
            // Comma prior to every argument except the first.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2878
            if (!first) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2879
                expect(COMMARIGHT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2880
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2881
                first = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2882
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2883
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2884
            // Get and add parameter.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2885
            final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2886
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2887
            // ECMA 13.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2888
            verifyStrictIdent(ident, "function parameter");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2889
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2890
            parameters.add(ident);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2891
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2892
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2893
        parameters.trimToSize();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2894
        return parameters;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2895
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2896
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2897
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2898
     * FunctionBody :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2899
     *      SourceElements?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2900
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2901
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2902
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2903
     * Parse function body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2904
     * @return function node (body.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2905
     */
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2906
    private Block functionBody(final ParserContextFunctionNode functionNode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2907
        long lastToken = 0L;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2908
        ParserContextBlockNode body = null;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2909
        final long bodyToken = token;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2910
        Block functionBody;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2911
        int bodyFinish = 0;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2912
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2913
        final boolean parseBody;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2914
        Object endParserState = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2915
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2916
            // Create a new function block.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2917
            body = newBlock();
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2918
            assert functionNode != null;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2919
            final int functionId = functionNode.getId();
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2920
            parseBody = reparsedFunction == null || functionId <= reparsedFunction.getFunctionNodeId();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2921
            // Nashorn extension: expression closures
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  2922
            if (!env._no_syntax_extensions && type != LBRACE) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2923
                /*
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2924
                 * Example:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2925
                 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2926
                 * function square(x) x * x;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2927
                 * print(square(3));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2928
                 */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2929
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2930
                // just expression as function body
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2931
                final Expression expr = assignmentExpression(true);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2932
                lastToken = previousToken;
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2933
                functionNode.setLastToken(previousToken);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2934
                assert lc.getCurrentBlock() == lc.getFunctionBody(functionNode);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2935
                // EOL uses length field to store the line number
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2936
                final int lastFinish = Token.descPosition(lastToken) + (Token.descType(lastToken) == EOL ? 0 : Token.descLength(lastToken));
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2937
                // Only create the return node if we aren't skipping nested functions. Note that we aren't
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2938
                // skipping parsing of these extended functions; they're considered to be small anyway. Also,
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2939
                // they don't end with a single well known token, so it'd be very hard to get correctly (see
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2940
                // the note below for reasoning on skipping happening before instead of after RBRACE for
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2941
                // details).
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2942
                if (parseBody) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2943
                    final ReturnNode returnNode = new ReturnNode(functionNode.getLineNumber(), expr.getToken(), lastFinish, expr);
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2944
                    appendStatement(returnNode);
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2945
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2946
            } else {
26505
d29bf8787b43 8057931: Instead of not skipping small functions in parser, make lexer avoid them instead
attila
parents: 26503
diff changeset
  2947
                expectDontAdvance(LBRACE);
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2948
                if (parseBody || !skipFunctionBody(functionNode)) {
26505
d29bf8787b43 8057931: Instead of not skipping small functions in parser, make lexer avoid them instead
attila
parents: 26503
diff changeset
  2949
                    next();
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2950
                    // Gather the function elements.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2951
                    final List<Statement> prevFunctionDecls = functionDeclarations;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2952
                    functionDeclarations = new ArrayList<>();
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2953
                    try {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2954
                        sourceElements(false);
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2955
                        addFunctionDeclarations(functionNode);
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2956
                    } finally {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2957
                        functionDeclarations = prevFunctionDecls;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2958
                    }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2959
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2960
                    lastToken = token;
26505
d29bf8787b43 8057931: Instead of not skipping small functions in parser, make lexer avoid them instead
attila
parents: 26503
diff changeset
  2961
                    if (parseBody) {
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2962
                        // Since the lexer can read ahead and lexify some number of tokens in advance and have
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2963
                        // them buffered in the TokenStream, we need to produce a lexer state as it was just
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2964
                        // before it lexified RBRACE, and not whatever is its current (quite possibly well read
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2965
                        // ahead) state.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2966
                        endParserState = new ParserState(Token.descPosition(token), line, linePosition);
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2967
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2968
                        // NOTE: you might wonder why do we capture/restore parser state before RBRACE instead of
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2969
                        // after RBRACE; after all, we could skip the below "expect(RBRACE);" if we captured the
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2970
                        // state after it. The reason is that RBRACE is a well-known token that we can expect and
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2971
                        // will never involve us getting into a weird lexer state, and as such is a great reparse
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2972
                        // point. Typical example of a weird lexer state after RBRACE would be:
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2973
                        //     function this_is_skipped() { ... } "use strict";
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2974
                        // because lexer is doing weird off-by-one maneuvers around string literal quotes. Instead
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2975
                        // of compensating for the possibility of a string literal (or similar) after RBRACE,
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2976
                        // we'll rather just restart parsing from this well-known, friendly token instead.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2977
                    }
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2978
                }
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2979
                bodyFinish = finish;
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2980
                functionNode.setLastToken(token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2981
                expect(RBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2982
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2983
        } finally {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2984
            restoreBlock(body);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2985
        }
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2986
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2987
        // NOTE: we can only do alterations to the function node after restoreFunctionNode.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2988
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2989
        if (parseBody) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2990
            functionNode.setEndParserState(endParserState);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2991
        } else if (!body.getStatements().isEmpty()){
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2992
            // This is to ensure the body is empty when !parseBody but we couldn't skip parsing it (see
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2993
            // skipFunctionBody() for possible reasons). While it is not strictly necessary for correctness to
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2994
            // enforce empty bodies in nested functions that were supposed to be skipped, we do assert it as
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2995
            // an invariant in few places in the compiler pipeline, so for consistency's sake we'll throw away
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2996
            // nested bodies early if we were supposed to skip 'em.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  2997
            body.setStatements(Collections.<Statement>emptyList());
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2998
        }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  2999
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3000
        if (reparsedFunction != null) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3001
            // We restore the flags stored in the function's ScriptFunctionData that we got when we first
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3002
            // eagerly parsed the code. We're doing it because some flags would be set based on the
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3003
            // content of the function, or even content of its nested functions, most of which are normally
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3004
            // skipped during an on-demand compilation.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3005
            final RecompilableScriptFunctionData data = reparsedFunction.getScriptFunctionData(functionNode.getId());
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3006
            if (data != null) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3007
                // Data can be null if when we originally parsed the file, we removed the function declaration
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3008
                // as it was dead code.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3009
                functionNode.setFlag(data.getFunctionFlags());
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3010
                // This compensates for missing markEval() in case the function contains an inner function
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3011
                // that contains eval(), that now we didn't discover since we skipped the inner function.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3012
                if (functionNode.hasNestedEval()) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3013
                    assert functionNode.hasScopeBlock();
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3014
                    body.setFlag(Block.NEEDS_SCOPE);
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3015
                }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3016
            }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3017
        }
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3018
        functionBody = new Block(bodyToken, bodyFinish, body.getFlags(), body.getStatements());
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3019
        return functionBody;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3020
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3021
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3022
    private boolean skipFunctionBody(final ParserContextFunctionNode functionNode) {
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3023
        if (reparsedFunction == null) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3024
            // Not reparsing, so don't skip any function body.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3025
            return false;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3026
        }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3027
        // Skip to the RBRACE of this function, and continue parsing from there.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3028
        final RecompilableScriptFunctionData data = reparsedFunction.getScriptFunctionData(functionNode.getId());
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3029
        if (data == null) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3030
            // Nested function is not known to the reparsed function. This can happen if the FunctionNode was
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3031
            // in dead code that was removed. Both FoldConstants and Lower prune dead code. In that case, the
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3032
            // FunctionNode was dropped before a RecompilableScriptFunctionData could've been created for it.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3033
            return false;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3034
        }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3035
        final ParserState parserState = (ParserState)data.getEndParserState();
26505
d29bf8787b43 8057931: Instead of not skipping small functions in parser, make lexer avoid them instead
attila
parents: 26503
diff changeset
  3036
        assert parserState != null;
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3037
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3038
        stream.reset();
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  3039
        lexer = parserState.createLexer(source, lexer, stream, scripting && !env._no_syntax_extensions, env._es6);
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3040
        line = parserState.line;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3041
        linePosition = parserState.linePosition;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3042
        // Doesn't really matter, but it's safe to treat it as if there were a semicolon before
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3043
        // the RBRACE.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3044
        type = SEMICOLON;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3045
        k = -1;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3046
        next();
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3047
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3048
        return true;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3049
    }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3050
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3051
    /**
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3052
     * Encapsulates part of the state of the parser, enough to reconstruct the state of both parser and lexer
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3053
     * for resuming parsing after skipping a function body.
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3054
     */
26646
332e9901f0ed 8058304: Non-serializable fields in serializable classes
hannesw
parents: 26505
diff changeset
  3055
    private static class ParserState implements Serializable {
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3056
        private final int position;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3057
        private final int line;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3058
        private final int linePosition;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3059
26646
332e9901f0ed 8058304: Non-serializable fields in serializable classes
hannesw
parents: 26505
diff changeset
  3060
        private static final long serialVersionUID = -2382565130754093694L;
332e9901f0ed 8058304: Non-serializable fields in serializable classes
hannesw
parents: 26505
diff changeset
  3061
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3062
        ParserState(final int position, final int line, final int linePosition) {
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3063
            this.position = position;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3064
            this.line = line;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3065
            this.linePosition = linePosition;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3066
        }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3067
32444
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  3068
        Lexer createLexer(final Source source, final Lexer lexer, final TokenStream stream, final boolean scripting, final boolean es6) {
4c7a40aab132 8134873: Implement support for ES6 numeric literals
aw
parents: 32437
diff changeset
  3069
            final Lexer newLexer = new Lexer(source, position, lexer.limit - position, stream, scripting, es6, true);
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3070
            newLexer.restoreState(new Lexer.State(position, Integer.MAX_VALUE, line, -1, linePosition, SEMICOLON));
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3071
            return newLexer;
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3072
        }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3073
    }
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3074
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3075
    private void printAST(final FunctionNode functionNode) {
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3076
        if (functionNode.getFlag(FunctionNode.IS_PRINT_AST)) {
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3077
            env.getErr().println(new ASTWriter(functionNode));
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3078
        }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3079
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3080
        if (functionNode.getFlag(FunctionNode.IS_PRINT_PARSE)) {
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3081
            env.getErr().println(new PrintVisitor(functionNode, true, false));
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3082
        }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3083
    }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  3084
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3085
    private void addFunctionDeclarations(final ParserContextFunctionNode functionNode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3086
        VarNode lastDecl = null;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3087
        for (int i = functionDeclarations.size() - 1; i >= 0; i--) {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3088
            Statement decl = functionDeclarations.get(i);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3089
            if (lastDecl == null && decl instanceof VarNode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3090
                decl = lastDecl = ((VarNode)decl).setFlag(VarNode.IS_LAST_FUNCTION_DECLARATION);
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3091
                functionNode.setFlag(FunctionNode.HAS_FUNCTION_DECLARATIONS);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3092
            }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3093
            prependStatement(decl);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3094
        }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3095
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3096
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3097
    private RuntimeNode referenceError(final Expression lhs, final Expression rhs, final boolean earlyError) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3098
        if (earlyError) {
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3099
            throw error(JSErrorType.REFERENCE_ERROR, AbstractParser.message("invalid.lvalue"), lhs.getToken());
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3100
        }
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3101
        final ArrayList<Expression> args = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3102
        args.add(lhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3103
        if (rhs == null) {
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  3104
            args.add(LiteralNode.newInstance(lhs.getToken(), lhs.getFinish()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3105
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3106
            args.add(rhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3107
        }
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  3108
        args.add(LiteralNode.newInstance(lhs.getToken(), lhs.getFinish(), lhs.toString()));
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  3109
        return new RuntimeNode(lhs.getToken(), lhs.getFinish(), RuntimeNode.Request.REFERENCE_ERROR, args);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3110
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3111
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3112
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3113
     * PostfixExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3114
     *      LeftHandSideExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3115
     *      LeftHandSideExpression ++ // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3116
     *      LeftHandSideExpression -- // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3117
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3118
     * See 11.3
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3119
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3120
     * UnaryExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3121
     *      PostfixExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3122
     *      delete UnaryExpression
32437
153cb8aeb422 8134865: Need to restore for container block from lexical context in finally
aw
parents: 32245
diff changeset
  3123
     *      void UnaryExpression
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3124
     *      typeof UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3125
     *      ++ UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3126
     *      -- UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3127
     *      + UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3128
     *      - UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3129
     *      ~ UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3130
     *      ! UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3131
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3132
     * See 11.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3133
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3134
     * Parse unary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3135
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3136
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3137
    private Expression unaryExpression() {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3138
        final int  unaryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3139
        final long unaryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3140
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3141
        switch (type) {
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3142
        case DELETE: {
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3143
            next();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3144
            final Expression expr = unaryExpression();
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3145
            if (expr instanceof BaseNode || expr instanceof IdentNode) {
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3146
                return new UnaryNode(unaryToken, expr);
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3147
            }
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3148
            appendStatement(new ExpressionStatement(unaryLine, unaryToken, finish, expr));
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3149
            return LiteralNode.newInstance(unaryToken, finish, true);
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3150
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3151
        case VOID:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3152
        case TYPEOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3153
        case ADD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3154
        case SUB:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3155
        case BIT_NOT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3156
        case NOT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3157
            next();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3158
            final Expression expr = unaryExpression();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  3159
            return new UnaryNode(unaryToken, expr);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3160
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3161
        case INCPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3162
        case DECPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3163
            final TokenType opType = type;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3164
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3165
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3166
            final Expression lhs = leftHandSideExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3167
            // ++, -- without operand..
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3168
            if (lhs == null) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3169
                throw error(AbstractParser.message("expected.lvalue", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3170
            }
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3171
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3172
            if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3173
                  lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3174
                  lhs instanceof IdentNode)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3175
                return referenceError(lhs, null, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3176
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3177
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3178
            if (lhs instanceof IdentNode) {
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  3179
                if (!checkIdentLValue((IdentNode)lhs)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3180
                    return referenceError(lhs, null, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3181
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3182
                verifyStrictIdent((IdentNode)lhs, "operand for " + opType.getName() + " operator");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3183
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3184
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3185
            return incDecExpression(unaryToken, opType, lhs, false);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3186
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3187
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3188
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3189
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3190
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3191
        Expression expression = leftHandSideExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3192
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3193
        if (last != EOL) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3194
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3195
            case INCPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3196
            case DECPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3197
                final TokenType opType = type;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3198
                final Expression lhs = expression;
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3199
                // ++, -- without operand..
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3200
                if (lhs == null) {
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3201
                    throw error(AbstractParser.message("expected.lvalue", type.getNameOrType()));
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3202
                }
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3203
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3204
                if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3205
                   lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3206
                   lhs instanceof IdentNode)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3207
                    next();
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3208
                    return referenceError(lhs, null, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3209
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3210
                if (lhs instanceof IdentNode) {
16523
af8b30edebce 8009718: Lazy execution architecture continued - ScriptFunctionData is either final or recompilable. Moved ScriptFunctionData creation logic away from runtime to compile time. Prepared for method generation/specialization. Got rid of ScriptFunctionImplTrampoline whose semantics could be done as part of the relinking anyway. Merge with the lookup package change.
lagergren
parents: 16262
diff changeset
  3211
                    if (!checkIdentLValue((IdentNode)lhs)) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3212
                        next();
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  3213
                        return referenceError(lhs, null, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3214
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3215
                    verifyStrictIdent((IdentNode)lhs, "operand for " + opType.getName() + " operator");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3216
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3217
                expression = incDecExpression(token, type, expression, true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3218
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3219
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3220
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3221
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3222
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3223
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3224
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3225
        if (expression == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3226
            throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3227
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3228
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3229
        return expression;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3230
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3231
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3232
    /**
32245
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3233
     * {@code
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3234
     * MultiplicativeExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3235
     *      UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3236
     *      MultiplicativeExpression * UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3237
     *      MultiplicativeExpression / UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3238
     *      MultiplicativeExpression % UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3239
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3240
     * See 11.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3241
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3242
     * AdditiveExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3243
     *      MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3244
     *      AdditiveExpression + MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3245
     *      AdditiveExpression - MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3246
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3247
     * See 11.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3248
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3249
     * ShiftExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3250
     *      AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3251
     *      ShiftExpression << AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3252
     *      ShiftExpression >> AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3253
     *      ShiftExpression >>> AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3254
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3255
     * See 11.7
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3256
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3257
     * RelationalExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3258
     *      ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3259
     *      RelationalExpression < ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3260
     *      RelationalExpression > ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3261
     *      RelationalExpression <= ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3262
     *      RelationalExpression >= ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3263
     *      RelationalExpression instanceof ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3264
     *      RelationalExpression in ShiftExpression // if !noIf
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3265
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3266
     * See 11.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3267
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3268
     *      RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3269
     *      EqualityExpression == RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3270
     *      EqualityExpression != RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3271
     *      EqualityExpression === RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3272
     *      EqualityExpression !== RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3273
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3274
     * See 11.9
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3275
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3276
     * BitwiseANDExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3277
     *      EqualityExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3278
     *      BitwiseANDExpression & EqualityExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3279
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3280
     * BitwiseXORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3281
     *      BitwiseANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3282
     *      BitwiseXORExpression ^ BitwiseANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3283
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3284
     * BitwiseORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3285
     *      BitwiseXORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3286
     *      BitwiseORExpression | BitwiseXORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3287
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3288
     * See 11.10
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3289
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3290
     * LogicalANDExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3291
     *      BitwiseORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3292
     *      LogicalANDExpression && BitwiseORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3293
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3294
     * LogicalORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3295
     *      LogicalANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3296
     *      LogicalORExpression || LogicalANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3297
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3298
     * See 11.11
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3299
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3300
     * ConditionalExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3301
     *      LogicalORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3302
     *      LogicalORExpression ? AssignmentExpression : AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3303
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3304
     * See 11.12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3305
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3306
     * AssignmentExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3307
     *      ConditionalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3308
     *      LeftHandSideExpression AssignmentOperator AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3309
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3310
     * AssignmentOperator :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3311
     *      = *= /= %= += -= <<= >>= >>>= &= ^= |=
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3312
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3313
     * See 11.13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3314
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3315
     * Expression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3316
     *      AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3317
     *      Expression , AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3318
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3319
     * See 11.14
32245
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3320
     * }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3321
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3322
     * Parse expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3323
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3324
     */
32245
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3325
    protected Expression expression() {
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3326
        // This method is protected so that subclass can get details
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3327
        // at expression start point!
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3328
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3329
        // Include commas in expression parsing.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3330
        return expression(unaryExpression(), COMMARIGHT.getPrecedence(), false);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3331
    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3332
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3333
    private JoinPredecessorExpression joinPredecessorExpression() {
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3334
        return new JoinPredecessorExpression(expression());
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3335
    }
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3336
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3337
    private Expression expression(final Expression exprLhs, final int minPrecedence, final boolean noIn) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3338
        // Get the precedence of the next operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3339
        int precedence = type.getPrecedence();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3340
        Expression lhs = exprLhs;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3341
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3342
        // While greater precedence.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3343
        while (type.isOperator(noIn) && precedence >= minPrecedence) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3344
            // Capture the operator token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3345
            final long op = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3346
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3347
            if (type == TERNARY) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3348
                // Skip operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3349
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3350
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3351
                // Pass expression. Middle expression of a conditional expression can be a "in"
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3352
                // expression - even in the contexts where "in" is not permitted.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3353
                final Expression trueExpr = expression(unaryExpression(), ASSIGN.getPrecedence(), false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3354
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3355
                expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3356
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3357
                // Fail expression.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3358
                final Expression falseExpr = expression(unaryExpression(), ASSIGN.getPrecedence(), noIn);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3359
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3360
                // Build up node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3361
                lhs = new TernaryNode(op, lhs, new JoinPredecessorExpression(trueExpr), new JoinPredecessorExpression(falseExpr));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3362
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3363
                // Skip operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3364
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3365
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3366
                 // Get the next primary expression.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3367
                Expression rhs;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3368
                final boolean isAssign = Token.descType(op) == ASSIGN;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3369
                if(isAssign) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3370
                    defaultNames.push(lhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3371
                }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3372
                try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3373
                    rhs = unaryExpression();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3374
                    // Get precedence of next operator.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3375
                    int nextPrecedence = type.getPrecedence();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3376
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3377
                    // Subtask greater precedence.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3378
                    while (type.isOperator(noIn) &&
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3379
                           (nextPrecedence > precedence ||
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3380
                           nextPrecedence == precedence && !type.isLeftAssociative())) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3381
                        rhs = expression(rhs, nextPrecedence, noIn);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3382
                        nextPrecedence = type.getPrecedence();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3383
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3384
                } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3385
                    if(isAssign) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3386
                        defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3387
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3388
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3389
                lhs = verifyAssignment(op, lhs, rhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3390
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3391
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3392
            precedence = type.getPrecedence();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3393
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3394
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3395
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3396
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3397
32245
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3398
    protected Expression assignmentExpression(final boolean noIn) {
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3399
        // This method is protected so that subclass can get details
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3400
        // at assignment expression start point!
80164edf8a10 8133872: Expression completion should work on contexts where an expression is accepted
sundar
parents: 31485
diff changeset
  3401
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3402
        // Exclude commas in expression parsing.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3403
        return expression(unaryExpression(), ASSIGN.getPrecedence(), noIn);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3404
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3405
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3406
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3407
     * Parse an end of line.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3408
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3409
    private void endOfLine() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3410
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3411
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3412
        case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3413
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3414
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3415
        case RPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3416
        case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3417
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3418
        case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3419
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3420
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3421
            if (last != EOL) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3422
                expect(SEMICOLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3423
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3424
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3425
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3426
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3427
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3428
    @Override
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3429
    public String toString() {
24759
31aed7d9c02a 8034206: Make parts of code pipeline reusable in order to facilitate faster warmup and faster lazy compilation.
lagergren
parents: 24751
diff changeset
  3430
        return "'JavaScript Parsing'";
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3431
    }
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3432
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3433
    private static void markEval(final ParserContext lc) {
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3434
        final Iterator<ParserContextFunctionNode> iter = lc.getFunctions();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3435
        boolean flaggedCurrentFn = false;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3436
        while (iter.hasNext()) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3437
            final ParserContextFunctionNode fn = iter.next();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3438
            if (!flaggedCurrentFn) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3439
                fn.setFlag(FunctionNode.HAS_EVAL);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3440
                flaggedCurrentFn = true;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3441
            } else {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3442
                fn.setFlag(FunctionNode.HAS_NESTED_EVAL);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3443
            }
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3444
            final ParserContextBlockNode body = lc.getFunctionBody(fn);
26503
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3445
            // NOTE: it is crucial to mark the body of the outer function as needing scope even when we skip
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3446
            // parsing a nested function. functionBody() contains code to compensate for the lack of invoking
3ed48a01100c 8057148: Skip nested functions on reparse
attila
parents: 26377
diff changeset
  3447
            // this method when the parser skips a nested function.
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3448
            body.setFlag(Block.NEEDS_SCOPE);
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3449
            fn.setFlag(FunctionNode.HAS_SCOPE_BLOCK);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3450
        }
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3451
    }
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3452
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3453
    private void prependStatement(final Statement statement) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3454
        lc.prependStatementToCurrentNode(statement);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3455
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3456
17524
703643aeb0d6 8013914: Removed explicit LineNumberNodes that were too brittle when code moves around, and also introduced unnecessary footprint. Introduced the Statement node and fixed dead code elimination issues that were discovered by the absense of labels for LineNumberNodes.
lagergren
parents: 17523
diff changeset
  3457
    private void appendStatement(final Statement statement) {
27102
c64b3468d51d 8012518: Reengineer Parser.java to make it play well with the copy-on-write IR.
lagergren
parents: 26646
diff changeset
  3458
        lc.appendStatementToCurrentNode(statement);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3459
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3460
}