nashorn/src/jdk/nashorn/internal/parser/Parser.java
author sundar
Thu, 14 Aug 2014 18:54:54 +0530
changeset 26065 d15adb218527
parent 26055 fe8be844ba50
permissions -rw-r--r--
8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally Reviewed-by: attila, jlaskey
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;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    48
import static jdk.nashorn.internal.parser.TokenType.LPAREN;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    49
import static jdk.nashorn.internal.parser.TokenType.RBRACE;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    50
import static jdk.nashorn.internal.parser.TokenType.RBRACKET;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    51
import static jdk.nashorn.internal.parser.TokenType.RPAREN;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    52
import static jdk.nashorn.internal.parser.TokenType.SEMICOLON;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    53
import static jdk.nashorn.internal.parser.TokenType.TERNARY;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    54
import static jdk.nashorn.internal.parser.TokenType.WHILE;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    55
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    56
import java.util.ArrayDeque;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    57
import java.util.ArrayList;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    58
import java.util.Collections;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
    59
import java.util.Deque;
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
    60
import java.util.HashMap;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    61
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
    62
import java.util.Iterator;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    63
import java.util.List;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    64
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
    65
import jdk.internal.dynalink.support.NameCodec;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
    66
import jdk.nashorn.internal.codegen.CompilerConstants;
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
    67
import jdk.nashorn.internal.codegen.Namespace;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    68
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
    69
import jdk.nashorn.internal.ir.BaseNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    70
import jdk.nashorn.internal.ir.BinaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    71
import jdk.nashorn.internal.ir.Block;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
    72
import jdk.nashorn.internal.ir.BlockLexicalContext;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    73
import jdk.nashorn.internal.ir.BlockStatement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    74
import jdk.nashorn.internal.ir.BreakNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    75
import jdk.nashorn.internal.ir.BreakableNode;
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;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    80
import jdk.nashorn.internal.ir.EmptyNode;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    81
import jdk.nashorn.internal.ir.Expression;
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
    82
import jdk.nashorn.internal.ir.ExpressionStatement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    83
import jdk.nashorn.internal.ir.ForNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    84
import jdk.nashorn.internal.ir.FunctionNode;
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
    85
import jdk.nashorn.internal.ir.FunctionNode.CompilationState;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    86
import jdk.nashorn.internal.ir.IdentNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    87
import jdk.nashorn.internal.ir.IfNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    88
import jdk.nashorn.internal.ir.IndexNode;
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
    89
import jdk.nashorn.internal.ir.JoinPredecessorExpression;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    90
import jdk.nashorn.internal.ir.LabelNode;
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
    91
import jdk.nashorn.internal.ir.LexicalContext;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    92
import jdk.nashorn.internal.ir.LiteralNode;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
    93
import jdk.nashorn.internal.ir.LoopNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    94
import jdk.nashorn.internal.ir.Node;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    95
import jdk.nashorn.internal.ir.ObjectNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    96
import jdk.nashorn.internal.ir.PropertyKey;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    97
import jdk.nashorn.internal.ir.PropertyNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    98
import jdk.nashorn.internal.ir.ReturnNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
    99
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
   100
import jdk.nashorn.internal.ir.Statement;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   101
import jdk.nashorn.internal.ir.SwitchNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   102
import jdk.nashorn.internal.ir.TernaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   103
import jdk.nashorn.internal.ir.ThrowNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   104
import jdk.nashorn.internal.ir.TryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   105
import jdk.nashorn.internal.ir.UnaryNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   106
import jdk.nashorn.internal.ir.VarNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   107
import jdk.nashorn.internal.ir.WhileNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   108
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
   109
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
   110
import jdk.nashorn.internal.ir.debug.PrintVisitor;
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   111
import jdk.nashorn.internal.runtime.Context;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   112
import jdk.nashorn.internal.runtime.ErrorManager;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   113
import jdk.nashorn.internal.runtime.JSErrorType;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   114
import jdk.nashorn.internal.runtime.ParserException;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   115
import jdk.nashorn.internal.runtime.RecompilableScriptFunctionData;
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   116
import jdk.nashorn.internal.runtime.ScriptEnvironment;
16245
6a1c6c8bc113 8008371: Fix Dynalink compiler warnings and whitespace
attila
parents: 16239
diff changeset
   117
import jdk.nashorn.internal.runtime.ScriptingFunctions;
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   118
import jdk.nashorn.internal.runtime.Source;
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
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   138
    private final BlockLexicalContext lc = new BlockLexicalContext();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   139
    private final Deque<Object> defaultNames = new ArrayDeque<>();
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
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   149
    private int nextFunctionId;
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) {
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   172
        this(env, source, errors, strict, FunctionNode.FIRST_FUNCTION_ID, 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 nextFunctionId  starting value for assigning new unique ids to function nodes
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   183
     * @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
   184
     * @param log debug logger if one is needed
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   185
     */
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   186
    public Parser(final ScriptEnvironment env, final Source source, final ErrorManager errors, final boolean strict, final int nextFunctionId, final int lineOffset, final DebugLogger log) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   187
        super(source, errors, strict, lineOffset);
24745
3a6e1477362b 8041434: Add synchronization to the common global constants structure
lagergren
parents: 24744
diff changeset
   188
        this.env = env;
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   189
        this.namespace = new Namespace(env.getNamespace());
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   190
        this.nextFunctionId    = nextFunctionId;
16262
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) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   225
        defaultNames.push(new IdentNode(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
    /**
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   229
     * Execute parse and return the resulting function node.
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   230
     * Errors will be thrown and the error manager will contain information
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   231
     * if parsing should fail
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   232
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   233
     * This is the default parse call, which will name the function node
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   234
     * {code :program} {@link CompilerConstants#PROGRAM}
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   235
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   236
     * @return function node resulting from successful parse
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   237
     */
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   238
    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
   239
        return parse(PROGRAM.symbolName(), 0, source.getLength(), false);
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   240
    }
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   241
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
     * Execute parse and return the resulting function node.
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   244
     * Errors will be thrown and the error manager will contain information
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   245
     * if parsing should fail
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   246
     *
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   247
     * This should be used to create one and only one function node
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   248
     *
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   249
     * @param scriptName name for the script, given to the parsed FunctionNode
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   250
     * @param startPos start position in source
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   251
     * @param len length of parse
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   252
     * @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
   253
     * 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
   254
     * property getter or setter in an object literal.
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   255
     *
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   256
     * @return function node resulting from successful parse
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   257
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   258
    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
   259
        final boolean isTimingEnabled = env.isTimingEnabled();
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
   260
        final long t0 = isTimingEnabled ? System.currentTimeMillis() : 0L;
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   261
        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
   262
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   263
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   264
            stream = new TokenStream();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   265
            lexer  = new Lexer(source, startPos, len, stream, scripting && !env._no_syntax_extensions);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   266
            lexer.line = lexer.pendingLine = lineOffset + 1;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   267
            line = lineOffset;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   268
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   269
            // Set up first token (skips opening EOL.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   270
            k = -1;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   271
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   272
            // Begin parse.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   273
            return program(scriptName, allowPropertyFunction);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   274
        } catch (final Exception e) {
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   275
            handleParseException(e);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   276
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   277
            return null;
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   278
        } finally {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   279
            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
   280
            if (isTimingEnabled) {
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
   281
                env._timing.accumulateTime(toString(), System.currentTimeMillis() - t0);
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   282
                log.info(end, "' in ", System.currentTimeMillis() - t0, " ms");
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   283
            } else {
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
   284
                log.info(end);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   285
            }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   286
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   287
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   288
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   289
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   290
     * Parse and return the list of function parameter list. A comma
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   291
     * separated list of function parameter identifiers is expected to be parsed.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   292
     * Errors will be thrown and the error manager will contain information
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   293
     * 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
   294
     * passed to "Function" constructor is a valid or not.
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
     * @return the list of IdentNodes representing the formal parameter list
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
    public List<IdentNode> parseFormalParameterList() {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   299
        try {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   300
            stream = new TokenStream();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   301
            lexer  = new Lexer(source, stream, scripting && !env._no_syntax_extensions);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   302
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   303
            // Set up first token (skips opening EOL.)
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   304
            k = -1;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   305
            next();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   306
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   307
            return formalParameterList(TokenType.EOF);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   308
        } catch (final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   309
            handleParseException(e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   310
            return null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   311
        }
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
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   314
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   315
     * Execute parse and return the resulting function node.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   316
     * Errors will be thrown and the error manager will contain information
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   317
     * 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
   318
     * passed to "Function" constructor is a valid function body or not.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   319
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   320
     * @return function node resulting from successful parse
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
    public FunctionNode parseFunctionBody() {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   323
        try {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   324
            stream = new TokenStream();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   325
            lexer  = new Lexer(source, stream, scripting && !env._no_syntax_extensions);
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
   326
            final int functionLine = line;
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   327
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   328
            // Set up first token (skips opening EOL.)
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   329
            k = -1;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   330
            next();
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
            // Make a fake token for the function.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   333
            final long functionToken = Token.toDesc(FUNCTION, 0, source.getLength());
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   334
            // Set up the function to append elements.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   335
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   336
            FunctionNode function = newFunctionNode(
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   337
                functionToken,
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   338
                new IdentNode(functionToken, Token.descPosition(functionToken), PROGRAM.symbolName()),
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   339
                new ArrayList<IdentNode>(),
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   340
                FunctionNode.Kind.NORMAL,
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   341
                functionLine);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   342
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   343
            functionDeclarations = new ArrayList<>();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   344
            sourceElements(false);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   345
            addFunctionDeclarations(function);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   346
            functionDeclarations = null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   347
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   348
            expect(EOF);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   349
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   350
            function.setFinish(source.getLength() - 1);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   351
            function = restoreFunctionNode(function, token); //commit code
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   352
            function = function.setBody(lc, function.getBody().setNeedsScope(lc));
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   353
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   354
            printAST(function);
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   355
            return function;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   356
        } catch (final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   357
            handleParseException(e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   358
            return null;
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   359
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   360
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   361
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   362
    private void handleParseException(final Exception e) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   363
        // Extract message from exception.  The message will be in error
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   364
        // message format.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   365
        String message = e.getMessage();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   366
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   367
        // If empty message.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   368
        if (message == null) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   369
            message = e.toString();
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   370
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   371
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   372
        // Issue message.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   373
        if (e instanceof ParserException) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   374
            errors.error((ParserException)e);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   375
        } else {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   376
            errors.error(message);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   377
        }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   378
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   379
        if (env._dump_on_error) {
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   380
            e.printStackTrace(env.getErr());
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
   381
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   382
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   383
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   384
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   385
     * Skip to a good parsing recovery point.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   386
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   387
    private void recover(final Exception e) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   388
        if (e != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   389
            // Extract message from exception.  The message will be in error
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   390
            // message format.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   391
            String message = e.getMessage();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   392
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   393
            // If empty message.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   394
            if (message == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   395
                message = e.toString();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   396
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   397
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   398
            // Issue message.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   399
            if (e instanceof ParserException) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   400
                errors.error((ParserException)e);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   401
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   402
                errors.error(message);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   403
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   404
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   405
            if (env._dump_on_error) {
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
   406
                e.printStackTrace(env.getErr());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   407
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   408
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   409
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   410
        // Skip to a recovery point.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   411
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   412
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   413
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   414
            case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   415
                // Can not go any further.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   416
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   417
            case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   418
            case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   419
            case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   420
                // Good recovery points.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   421
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   422
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   423
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   424
                // So we can recover after EOL.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   425
                nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   426
                break;
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
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   431
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   432
     * Set up a new block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   433
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   434
     * @return New block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   435
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   436
    private Block newBlock() {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   437
        return lc.push(new Block(token, Token.descPosition(token)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   438
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   439
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   440
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   441
     * Set up a new function block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   442
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   443
     * @param ident Name of function.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   444
     * @return New block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   445
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   446
    private FunctionNode newFunctionNode(final long startToken, final IdentNode ident, final List<IdentNode> parameters, final FunctionNode.Kind kind, final int functionLine) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   447
        // Build function name.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   448
        final StringBuilder sb = new StringBuilder();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   449
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   450
        final FunctionNode parentFunction = lc.getCurrentFunction();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   451
        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
   452
            sb.append(parentFunction.getName()).append('$');
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   453
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   454
22374
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   455
        assert ident.getName() != null;
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   456
        sb.append(ident.getName());
5231ab59e740 8030809: Anonymous functions should not be shown with internal names in script stack trace
sundar
parents: 21868
diff changeset
   457
16233
95d3e01c04c3 8008199: Lazy compilation and trampoline implementation
lagergren
parents: 16211
diff changeset
   458
        final String name = namespace.uniqueName(sb.toString());
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   459
        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
   460
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   461
        int flags = 0;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   462
        if (isStrictMode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   463
            flags |= FunctionNode.IS_STRICT;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   464
        }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   465
        if (parentFunction == null) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   466
            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
   467
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   468
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   469
        // Start new block.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   470
        final FunctionNode functionNode =
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   471
            new FunctionNode(
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   472
                source,
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   473
                nextFunctionId++,
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   474
                functionLine,
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   475
                token,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   476
                Token.descPosition(token),
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   477
                startToken,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   478
                namespace,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   479
                ident,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   480
                name,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   481
                parameters,
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   482
                kind,
26055
fe8be844ba50 8043956: Make code caching work with optimistic typing and lazy compilation
hannesw
parents: 24994
diff changeset
   483
                flags);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   484
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   485
        lc.push(functionNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   486
        // Create new block, and just put it on the context stack, restoreFunctionNode() will associate it with the
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   487
        // FunctionNode.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   488
        newBlock();
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
   489
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   490
        return functionNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   491
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   492
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   493
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   494
     * Restore the current block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   495
     */
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   496
    private Block restoreBlock(final Block 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
   497
        return lc.pop(block);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   498
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   499
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
   500
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   501
    private FunctionNode restoreFunctionNode(final FunctionNode functionNode, final long lastToken) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   502
        final Block newBody = restoreBlock(lc.getFunctionBody(functionNode));
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   503
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
   504
        return lc.pop(functionNode).
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
   505
            setBody(lc, newBody).
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
   506
            setLastToken(lc, lastToken).
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   507
            setState(lc, errors.hasErrors() ? CompilationState.PARSE_ERROR : CompilationState.PARSED);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   508
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   509
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   510
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   511
     * Get the statements in a block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   512
     * @return Block statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   513
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   514
    private Block getBlock(final boolean needsBraces) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   515
        // Set up new block. Captures LBRACE.
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   516
        Block newBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   517
        try {
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   518
            // Block opening brace.
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   519
            if (needsBraces) {
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   520
                expect(LBRACE);
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   521
            }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   522
            // Accumulate block statements.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   523
            statementList();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   524
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   525
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   526
            newBlock = restoreBlock(newBlock);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   527
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   528
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
   529
        final int possibleEnd = Token.descPosition(token) + Token.descLength(token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   530
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   531
        // Block closing brace.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   532
        if (needsBraces) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   533
            expect(RBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   534
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   535
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   536
        newBlock.setFinish(possibleEnd);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   537
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   538
        return newBlock;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   539
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   540
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   541
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   542
     * Get all the statements generated by a single statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   543
     * @return Statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   544
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   545
    private Block getStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   546
        if (type == LBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   547
            return getBlock(true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   548
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   549
        // Set up new block. Captures first token.
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   550
        Block newBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   551
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   552
            statement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   553
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   554
            newBlock = restoreBlock(newBlock);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   555
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   556
        return newBlock;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   557
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   558
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   559
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   560
     * Detect calls to special functions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   561
     * @param ident Called function.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   562
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   563
    private void detectSpecialFunction(final IdentNode ident) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   564
        final String name = ident.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   565
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   566
        if (EVAL.symbolName().equals(name)) {
17255
aa61d23e36e5 8013419: Streamline handling of with and eval
attila
parents: 17249
diff changeset
   567
            markEval(lc);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   568
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   569
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   570
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   571
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   572
     * Detect use of special properties.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   573
     * @param ident Referenced property.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   574
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   575
    private void detectSpecialProperty(final IdentNode ident) {
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   576
        if (isArguments(ident)) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   577
            lc.setFlag(lc.getCurrentFunction(), FunctionNode.USES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   578
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   579
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   580
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   581
    private static boolean isArguments(final String name) {
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   582
        return ARGUMENTS_NAME.equals(name);
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   583
    }
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   584
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   585
    private static boolean isArguments(final IdentNode ident) {
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   586
        return isArguments(ident.getName());
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   587
    }
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
   588
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   589
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   590
     * Tells whether a IdentNode can be used as L-value of an assignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   591
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   592
     * @param ident IdentNode to be checked
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   593
     * @return whether the ident can be used as L-value
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   594
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   595
    private static boolean checkIdentLValue(final IdentNode ident) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   596
        return Token.descType(ident.getToken()).getKind() != TokenKind.KEYWORD;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   597
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   598
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   599
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   600
     * Verify an assignment expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   601
     * @param op  Operation token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   602
     * @param lhs Left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   603
     * @param rhs Right hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   604
     * @return Verified expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   605
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   606
    private Expression verifyAssignment(final long op, final Expression lhs, final Expression rhs) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   607
        final TokenType opType = Token.descType(op);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   608
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   609
        switch (opType) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   610
        case ASSIGN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   611
        case ASSIGN_ADD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   612
        case ASSIGN_BIT_AND:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   613
        case ASSIGN_BIT_OR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   614
        case ASSIGN_BIT_XOR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   615
        case ASSIGN_DIV:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   616
        case ASSIGN_MOD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   617
        case ASSIGN_MUL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   618
        case ASSIGN_SAR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   619
        case ASSIGN_SHL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   620
        case ASSIGN_SHR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   621
        case ASSIGN_SUB:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   622
            if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   623
                  lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   624
                  lhs instanceof IdentNode)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
   625
                return referenceError(lhs, rhs, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   626
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   627
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   628
            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
   629
                if (!checkIdentLValue((IdentNode)lhs)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
   630
                    return referenceError(lhs, rhs, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   631
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   632
                verifyStrictIdent((IdentNode)lhs, "assignment");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   633
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   634
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   635
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   636
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   637
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   638
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   639
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   640
        // Build up node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   641
        if(BinaryNode.isLogical(opType)) {
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   642
            return new BinaryNode(op, new JoinPredecessorExpression(lhs), new JoinPredecessorExpression(rhs));
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   643
        }
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   644
        return new BinaryNode(op, lhs, rhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   645
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   646
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
   647
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   648
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   649
     * Reduce increment/decrement to simpler operations.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   650
     * @param firstToken First token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   651
     * @param tokenType  Operation token (INCPREFIX/DEC.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   652
     * @param expression Left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   653
     * @param isPostfix  Prefix or postfix.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   654
     * @return           Reduced expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   655
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   656
    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
   657
        if (isPostfix) {
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   658
            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
   659
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   660
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   661
        return new UnaryNode(firstToken, expression);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   662
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   663
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   664
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   665
     * -----------------------------------------------------------------------
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   666
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   667
     * Grammar based on
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   668
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   669
     *      ECMAScript Language Specification
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   670
     *      ECMA-262 5th Edition / December 2009
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   671
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   672
     * -----------------------------------------------------------------------
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
     * Program :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   677
     *      SourceElements?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   678
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   679
     * See 14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   680
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   681
     * Parse the top level script.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   682
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   683
    private FunctionNode program(final String scriptName, final boolean allowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   684
        // 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
   685
        final long functionToken = Token.toDesc(FUNCTION, Token.descPosition(Token.withDelimiter(token)), source.getLength());
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   686
        final int  functionLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   687
        // Set up the script to append elements.
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
   688
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   689
        FunctionNode script = newFunctionNode(
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   690
            functionToken,
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
   691
            new IdentNode(functionToken, Token.descPosition(functionToken), scriptName),
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   692
            new ArrayList<IdentNode>(),
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   693
            FunctionNode.Kind.SCRIPT,
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   694
            functionLine);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   695
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   696
        functionDeclarations = new ArrayList<>();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   697
        sourceElements(allowPropertyFunction);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   698
        addFunctionDeclarations(script);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
   699
        functionDeclarations = null;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   700
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   701
        expect(EOF);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   702
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   703
        script.setFinish(source.getLength() - 1);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   704
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   705
        script = restoreFunctionNode(script, token); //commit code
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   706
        script = script.setBody(lc, script.getBody().setNeedsScope(lc));
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
   707
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   708
        return script;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   709
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   710
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   711
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   712
     * Directive value or null if statement is not a directive.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   713
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   714
     * @param stmt Statement to be checked
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   715
     * @return Directive value if the given statement is a directive
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   716
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   717
    private String getDirective(final Node stmt) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   718
        if (stmt instanceof ExpressionStatement) {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   719
            final Node expr = ((ExpressionStatement)stmt).getExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   720
            if (expr instanceof LiteralNode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   721
                final LiteralNode<?> lit = (LiteralNode<?>)expr;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   722
                final long litToken = lit.getToken();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   723
                final TokenType tt = Token.descType(litToken);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   724
                // A directive is either a string or an escape string
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   725
                if (tt == TokenType.STRING || tt == TokenType.ESCSTRING) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   726
                    // Make sure that we don't unescape anything. Return as seen in source!
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   727
                    return source.getString(lit.getStart(), Token.descLength(litToken));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   728
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   729
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   730
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   731
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   732
        return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   733
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   734
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   735
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   736
     * SourceElements :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   737
     *      SourceElement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   738
     *      SourceElements SourceElement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   739
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   740
     * See 14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   741
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   742
     * Parse the elements of the script or function.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   743
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   744
    private void sourceElements(final boolean shouldAllowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   745
        List<Node>    directiveStmts        = null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   746
        boolean       checkDirective        = true;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   747
        boolean       allowPropertyFunction = shouldAllowPropertyFunction;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   748
        final boolean oldStrictMode         = isStrictMode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   749
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   750
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   751
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   752
            // If is a script, then process until the end of the script.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   753
            while (type != EOF) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   754
                // Break if the end of a code block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   755
                if (type == RBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   756
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   757
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   758
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   759
                try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   760
                    // Get the next element.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   761
                    statement(true, allowPropertyFunction);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   762
                    allowPropertyFunction = false;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   763
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   764
                    // check for directive prologues
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   765
                    if (checkDirective) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   766
                        // skip any debug statement like line number to get actual first line
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   767
                        final Node lastStatement = lc.getLastStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   768
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   769
                        // get directive prologue, if any
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   770
                        final String directive = getDirective(lastStatement);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   771
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   772
                        // If we have seen first non-directive statement,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   773
                        // no more directive statements!!
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   774
                        checkDirective = directive != null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   775
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   776
                        if (checkDirective) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   777
                            if (!oldStrictMode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   778
                                if (directiveStmts == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   779
                                    directiveStmts = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   780
                                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   781
                                directiveStmts.add(lastStatement);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   782
                            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   783
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   784
                            // handle use strict directive
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   785
                            if ("use strict".equals(directive)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   786
                                isStrictMode = true;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   787
                                final FunctionNode function = lc.getCurrentFunction();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   788
                                lc.setFlag(lc.getCurrentFunction(), FunctionNode.IS_STRICT);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   789
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   790
                                // We don't need to check these, if lexical environment is already strict
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   791
                                if (!oldStrictMode && directiveStmts != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   792
                                    // check that directives preceding this one do not violate strictness
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   793
                                    for (final Node statement : directiveStmts) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   794
                                        // the get value will force unescape of preceeding
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   795
                                        // escaped string directives
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   796
                                        getValue(statement.getToken());
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   797
                                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   798
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   799
                                    // 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
   800
                                    // satisfy strict mode restrictions.
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   801
                                    verifyStrictIdent(function.getIdent(), "function name");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   802
                                    for (final IdentNode param : function.getParameters()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   803
                                        verifyStrictIdent(param, "function parameter");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   804
                                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   805
                                }
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   806
                            } 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
   807
                                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
   808
                                if (flag != 0) {
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   809
                                    final FunctionNode function = lc.getCurrentFunction();
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   810
                                    lc.setFlag(function, flag);
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
   811
                                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   812
                            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   813
                        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   814
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   815
                } catch (final Exception e) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
   816
                    //recover parsing
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   817
                    recover(e);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   818
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   819
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   820
                // No backtracking from here on.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   821
                stream.commit(k);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   822
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   823
        } finally {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   824
            isStrictMode = oldStrictMode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   825
        }
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
     * Statement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   830
     *      Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   831
     *      VariableStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   832
     *      EmptyStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   833
     *      ExpressionStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   834
     *      IfStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   835
     *      IterationStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   836
     *      ContinueStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   837
     *      BreakStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   838
     *      ReturnStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   839
     *      WithStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   840
     *      LabelledStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   841
     *      SwitchStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   842
     *      ThrowStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   843
     *      TryStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   844
     *      DebuggerStatement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   845
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   846
     * see 12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   847
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   848
     * Parse any of the basic statement types.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   849
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   850
    private void statement() {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   851
        statement(false, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   852
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   853
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   854
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   855
     * @param topLevel does this statement occur at the "top level" of a script or a function?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   856
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   857
    private void statement(final boolean topLevel, final boolean allowPropertyFunction) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   858
        if (type == FUNCTION) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   859
            // As per spec (ECMA section 12), function declarations as arbitrary statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   860
            // 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
   861
            functionExpression(true, topLevel);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   862
            return;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   863
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   864
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   865
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   866
        case LBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   867
            block();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   868
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   869
        case VAR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   870
            variableStatement(true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   871
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   872
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   873
            emptyStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   874
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   875
        case IF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   876
            ifStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   877
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   878
        case FOR:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   879
            forStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   880
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   881
        case WHILE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   882
            whileStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   883
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   884
        case DO:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   885
            doStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   886
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   887
        case CONTINUE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   888
            continueStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   889
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   890
        case BREAK:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   891
            breakStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   892
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   893
        case RETURN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   894
            returnStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   895
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   896
        case YIELD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   897
            yieldStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   898
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   899
        case WITH:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   900
            withStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   901
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   902
        case SWITCH:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   903
            switchStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   904
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   905
        case THROW:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   906
            throwStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   907
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   908
        case TRY:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   909
            tryStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   910
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   911
        case DEBUGGER:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   912
            debuggerStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   913
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   914
        case RPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   915
        case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   916
        case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   917
            expect(SEMICOLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   918
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   919
        default:
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   920
            if (env._const_as_var && type == CONST) {
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   921
                variableStatement(true);
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   922
                break;
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   923
            }
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
   924
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   925
            if (type == IDENT || isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   926
                if (T(k + 1) == COLON) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   927
                    labelStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   928
                    return;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   929
                }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   930
                if(allowPropertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   931
                    final String ident = (String)getValue();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   932
                    final long propertyToken = token;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   933
                    final int propertyLine = line;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   934
                    if("get".equals(ident)) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   935
                        next();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   936
                        addPropertyFunctionStatement(propertyGetterFunction(propertyToken, propertyLine));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   937
                        return;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   938
                    } else if("set".equals(ident)) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   939
                        next();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   940
                        addPropertyFunctionStatement(propertySetterFunction(propertyToken, propertyLine));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   941
                        return;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   942
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   943
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   944
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   945
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   946
            expressionStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   947
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   948
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   949
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   950
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   951
    private void addPropertyFunctionStatement(final PropertyFunction propertyFunction) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   952
        final FunctionNode fn = propertyFunction.functionNode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   953
        functionDeclarations.add(new ExpressionStatement(fn.getLineNumber(), fn.getToken(), finish, fn));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   954
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
   955
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   956
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   957
     * block :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   958
     *      { StatementList? }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   959
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   960
     * see 12.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   961
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   962
     * Parse a statement block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   963
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   964
    private void block() {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
   965
        appendStatement(new BlockStatement(line, getBlock(true)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   966
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   967
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   968
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   969
     * StatementList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   970
     *      Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   971
     *      StatementList Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   972
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   973
     * See 12.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   974
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   975
     * Parse a list of statements.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   976
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   977
    private void statementList() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   978
        // Accumulate statements until end of list. */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   979
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   980
        while (type != EOF) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   981
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   982
            case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   983
            case CASE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   984
            case DEFAULT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   985
            case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   986
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   987
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   988
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   989
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   990
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   991
            // Get next statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   992
            statement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   993
        }
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
     * Make sure that in strict mode, the identifier name used is allowed.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   998
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
   999
     * @param ident         Identifier that is verified
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1000
     * @param contextString String used in error message to give context to the user
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1001
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1002
    private void verifyStrictIdent(final IdentNode ident, final String contextString) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1003
        if (isStrictMode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1004
            switch (ident.getName()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1005
            case "eval":
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1006
            case "arguments":
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1007
                throw error(AbstractParser.message("strict.name", ident.getName(), contextString), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1008
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1009
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1010
            }
20571
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1011
f52b0abf5d88 8026039: future strict names are allowed as function name and argument name of a strict function
sundar
parents: 20559
diff changeset
  1012
            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
  1013
                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
  1014
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1015
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1016
    }
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
     * VariableStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1020
     *      var VariableDeclarationList ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1021
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1022
     * VariableDeclarationList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1023
     *      VariableDeclaration
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1024
     *      VariableDeclarationList , VariableDeclaration
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1025
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1026
     * VariableDeclaration :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1027
     *      Identifier Initializer?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1028
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1029
     * Initializer :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1030
     *      = AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1031
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1032
     * See 12.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1033
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1034
     * Parse a VAR statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1035
     * @param isStatement True if a statement (not used in a FOR.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1036
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1037
    private List<VarNode> variableStatement(final boolean isStatement) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1038
        // VAR tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1039
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1040
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1041
        final List<VarNode> vars = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1042
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1043
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1044
            // 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
  1045
            final int  varLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1046
            final long varToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1047
            // Get name of var.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1048
            final IdentNode name = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1049
            verifyStrictIdent(name, "variable name");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1050
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1051
            // Assume no init.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1052
            Expression init = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1053
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1054
            // Look for initializer assignment.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1055
            if (type == ASSIGN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1056
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1057
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1058
                // Get initializer expression. Suppress IN if not statement.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1059
                defaultNames.push(name);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1060
                try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1061
                    init = assignmentExpression(!isStatement);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1062
                } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1063
                    defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  1064
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1065
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1066
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1067
            // Allocate var 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
  1068
            final VarNode var = new VarNode(varLine, varToken, finish, name, init);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1069
            vars.add(var);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1070
            appendStatement(var);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1071
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1072
            if (type != COMMARIGHT) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1073
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1074
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1075
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1076
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1077
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1078
        // If is a statement then handle end of line.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1079
        if (isStatement) {
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
  1080
            final boolean semicolon = type == SEMICOLON;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1081
            endOfLine();
16153
60de45bf54b0 8005703: Offsets miscalculated for blocks
jlaskey
parents: 16151
diff changeset
  1082
            if (semicolon) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1083
                lc.getCurrentBlock().setFinish(finish);
16153
60de45bf54b0 8005703: Offsets miscalculated for blocks
jlaskey
parents: 16151
diff changeset
  1084
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1085
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1086
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1087
        return vars;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1088
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1089
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1090
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1091
     * EmptyStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1092
     *      ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1093
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1094
     * See 12.3
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1095
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1096
     * Parse an empty statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1097
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1098
    private void emptyStatement() {
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  1099
        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
  1100
            appendStatement(new EmptyNode(line, token, Token.descPosition(token) + Token.descLength(token)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1101
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1102
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1103
        // SEMICOLON checked in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1104
        next();
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
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1108
     * ExpressionStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1109
     *      Expression ; // [lookahead ~( or  function )]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1110
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1111
     * See 12.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1112
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1113
     * Parse an expression used in a statement block.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1114
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1115
    private void expressionStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1116
        // 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
  1117
        final int  expressionLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1118
        final long expressionToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1119
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1120
        // Get expression and add as statement.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1121
        final Expression expression = expression();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1122
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1123
        ExpressionStatement expressionStatement = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1124
        if (expression != null) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1125
            expressionStatement = new ExpressionStatement(expressionLine, expressionToken, finish, expression);
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1126
            appendStatement(expressionStatement);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1127
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1128
            expect(null);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1129
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1130
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1131
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1132
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1133
        if (expressionStatement != null) {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1134
            expressionStatement.setFinish(finish);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1135
            lc.getCurrentBlock().setFinish(finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1136
        }
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
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1140
     * IfStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1141
     *      if ( Expression ) Statement else Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1142
     *      if ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1143
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1144
     * See 12.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1145
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1146
     * Parse an IF statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1147
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1148
    private void ifStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1149
        // 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
  1150
        final int  ifLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1151
        final long ifToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1152
         // IF tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1153
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1154
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1155
        expect(LPAREN);
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1156
        final Expression test = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1157
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1158
        final Block pass = getStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1159
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1160
        Block fail = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1161
        if (type == ELSE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1162
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1163
            fail = getStatement();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1164
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1165
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
  1166
        appendStatement(new IfNode(ifLine, ifToken, fail != null ? fail.getFinish() : pass.getFinish(), test, pass, fail));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1167
    }
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
     * ... IterationStatement:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1171
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1172
     *           for ( Expression[NoIn]?; Expression? ; Expression? ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1173
     *           for ( var VariableDeclarationList[NoIn]; Expression? ; Expression? ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1174
     *           for ( LeftHandSideExpression in Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1175
     *           for ( var VariableDeclaration[NoIn] in Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1176
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1177
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1178
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1179
     * Parse a FOR statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1180
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1181
    private void forStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1182
        // Create FOR node, capturing FOR token.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1183
        ForNode forNode = new ForNode(line, token, Token.descPosition(token), null, ForNode.IS_FOR);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1184
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1185
        lc.push(forNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1186
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1187
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1188
            // FOR tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1189
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1190
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1191
            // Nashorn extension: for each expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1192
            // 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
  1193
            if (!env._no_syntax_extensions && type == IDENT && "each".equals(getValue())) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1194
                forNode = forNode.setIsForEach(lc);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1195
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1196
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1197
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1198
            expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1199
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1200
            List<VarNode> vars = null;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1201
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1202
            switch (type) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1203
            case VAR:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1204
                // Var statements captured in for outer block.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1205
                vars = variableStatement(false);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1206
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1207
            case SEMICOLON:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1208
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1209
            default:
24279
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1210
                if (env._const_as_var && type == CONST) {
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1211
                    // Var statements captured in for outer block.
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1212
                    vars = variableStatement(false);
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1213
                    break;
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1214
                }
33b0fbd03872 8027933: Add --const-as-var option
sundar
parents: 23766
diff changeset
  1215
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1216
                final Expression expression = expression(unaryExpression(), COMMARIGHT.getPrecedence(), true);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1217
                forNode = forNode.setInit(lc, expression);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1218
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1219
            }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1220
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1221
            switch (type) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1222
            case SEMICOLON:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1223
                // for (init; test; modify)
18843
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1224
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1225
                // for each (init; test; modify) is invalid
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1226
                if (forNode.isForEach()) {
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1227
                    throw error(AbstractParser.message("for.each.without.in"), token);
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1228
                }
eea6d1b8263e 8019805: for each (init; test; modify) is invalid
sundar
parents: 18632
diff changeset
  1229
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1230
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1231
                if (type != SEMICOLON) {
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1232
                    forNode = forNode.setTest(lc, joinPredecessorExpression());
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1233
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1234
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1235
                if (type != RPAREN) {
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1236
                    forNode = forNode.setModify(lc, joinPredecessorExpression());
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1237
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1238
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1239
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1240
            case IN:
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1241
                forNode = forNode.setIsForIn(lc).setTest(lc, new JoinPredecessorExpression());
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1242
                if (vars != null) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1243
                    // for (var i in obj)
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1244
                    if (vars.size() == 1) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1245
                        forNode = forNode.setInit(lc, new IdentNode(vars.get(0).getName()));
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1246
                    } else {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1247
                        // for (var i, j in obj) is invalid
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1248
                        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
  1249
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1250
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1251
                } else {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1252
                    // for (expr in obj)
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1253
                    final Node init = forNode.getInit();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1254
                    assert init != null : "for..in init expression can not be null here";
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1255
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1256
                    // check if initial expression is a valid L-value
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1257
                    if (!(init instanceof AccessNode ||
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1258
                          init instanceof IndexNode ||
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1259
                          init instanceof IdentNode)) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1260
                        throw error(AbstractParser.message("not.lvalue.for.in.loop"), init.getToken());
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1261
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1262
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1263
                    if (init instanceof IdentNode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1264
                        if (!checkIdentLValue((IdentNode)init)) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1265
                            throw error(AbstractParser.message("not.lvalue.for.in.loop"), init.getToken());
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1266
                        }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1267
                        verifyStrictIdent((IdentNode)init, "for-in iterator");
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1268
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1269
                }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1270
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1271
                next();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1272
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1273
                // Get the collection expression.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1274
                forNode = forNode.setModify(lc, joinPredecessorExpression());
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1275
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1276
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1277
            default:
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1278
                expect(SEMICOLON);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1279
                break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1280
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1281
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1282
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1283
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1284
            // Set the for body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1285
            final Block body = getStatement();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1286
            forNode = forNode.setBody(lc, body);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1287
            forNode.setFinish(body.getFinish());
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1288
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1289
            appendStatement(forNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1290
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1291
            lc.pop(forNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1292
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1293
     }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1294
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1295
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1296
     * ... IterationStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1297
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1298
     *           Expression[NoIn]?; Expression? ; Expression?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1299
     *           var VariableDeclarationList[NoIn]; Expression? ; Expression?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1300
     *           LeftHandSideExpression in Expression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1301
     *           var VariableDeclaration[NoIn] in Expression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1302
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1303
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1304
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1305
     * Parse the control section of a FOR statement.  Also used for
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1306
     * comprehensions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1307
     * @param forNode Owning FOR.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1308
     */
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1309
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1310
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1311
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1312
     * ...IterationStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1313
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1314
     *           while ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1315
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1316
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1317
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1318
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1319
     * Parse while statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1320
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1321
    private void whileStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1322
        // Capture WHILE token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1323
        final long whileToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1324
        // WHILE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1325
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1326
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1327
        // Construct WHILE node.
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1328
        WhileNode whileNode = new WhileNode(line, whileToken, Token.descPosition(whileToken), false);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1329
        lc.push(whileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1330
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1331
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1332
            expect(LPAREN);
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1333
            final int whileLine = line;
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1334
            final JoinPredecessorExpression test = joinPredecessorExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1335
            expect(RPAREN);
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1336
            final Block body = getStatement();
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1337
            appendStatement(whileNode =
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1338
                new WhileNode(whileLine, whileToken, finish, false).
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1339
                    setTest(lc, test).
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1340
                    setBody(lc, body));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1341
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1342
            lc.pop(whileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1343
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1344
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1345
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1346
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1347
     * ...IterationStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1348
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1349
     *           do Statement while( Expression ) ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1350
     *           ...
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1351
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1352
     * See 12.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1353
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1354
     * Parse DO WHILE statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1355
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1356
    private void doStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1357
        // Capture DO token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1358
        final long doToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1359
        // DO tested in the caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1360
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1361
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1362
        WhileNode doWhileNode = new WhileNode(-1, doToken, Token.descPosition(doToken), true);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1363
        lc.push(doWhileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1364
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1365
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1366
           // Get DO body.
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1367
            final Block body = getStatement();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1368
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1369
            expect(WHILE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1370
            expect(LPAREN);
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1371
            final int doLine = line;
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1372
            final JoinPredecessorExpression test = joinPredecessorExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1373
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1374
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1375
            if (type == SEMICOLON) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1376
                endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1377
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1378
            doWhileNode.setFinish(finish);
21868
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1379
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1380
            //line number is last
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1381
            appendStatement(doWhileNode =
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1382
                new WhileNode(doLine, doToken, finish, true).
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1383
                    setBody(lc, body).
f3cd4fa7f8b9 8028434: Line number nodes were off for while nodes and do while nodes - the line number of a loop node should be treated as the location of the test expression
lagergren
parents: 20938
diff changeset
  1384
                    setTest(lc, test));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1385
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1386
            lc.pop(doWhileNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1387
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1388
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1389
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1390
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1391
     * ContinueStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1392
     *      continue Identifier? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1393
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1394
     * See 12.7
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1395
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1396
     * Parse CONTINUE statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1397
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1398
    private void continueStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1399
        // 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
  1400
        final int  continueLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1401
        final long continueToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1402
        // CONTINUE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1403
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1404
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1405
        LabelNode labelNode = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1406
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1407
        // SEMICOLON or label.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1408
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1409
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1410
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1411
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1412
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1413
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1414
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1415
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1416
            final IdentNode ident = getIdent();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1417
            labelNode = lc.findLabel(ident.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1418
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1419
            if (labelNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1420
                throw error(AbstractParser.message("undefined.label", ident.getName()), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1421
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1422
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1423
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1424
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1425
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1426
        final String labelName = labelNode == null ? null : labelNode.getLabelName();
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1427
        final LoopNode targetNode = lc.getContinueTo(labelName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1428
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1429
        if (targetNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1430
            throw error(AbstractParser.message("illegal.continue.stmt"), continueToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1431
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1432
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1433
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1434
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1435
        // Construct and add CONTINUE node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1436
        appendStatement(new ContinueNode(continueLine, continueToken, finish, labelName));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1437
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1438
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1439
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1440
     * BreakStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1441
     *      break Identifier? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1442
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1443
     * See 12.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1444
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1445
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1446
    private void breakStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1447
        // 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
  1448
        final int  breakLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1449
        final long breakToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1450
        // BREAK tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1451
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1452
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1453
        LabelNode labelNode = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1454
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1455
        // SEMICOLON or label.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1456
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1457
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1458
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1459
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1460
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1461
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1462
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1463
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1464
            final IdentNode ident = getIdent();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1465
            labelNode = lc.findLabel(ident.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1466
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1467
            if (labelNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1468
                throw error(AbstractParser.message("undefined.label", ident.getName()), ident.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1469
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1470
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1471
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1472
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1473
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1474
        //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
  1475
        //targetNode is what we are breaking out from.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1476
        final String labelName = labelNode == null ? null : labelNode.getLabelName();
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1477
        final BreakableNode targetNode = lc.getBreakable(labelName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1478
        if (targetNode == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1479
            throw error(AbstractParser.message("illegal.break.stmt"), breakToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1480
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1481
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1482
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1483
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1484
        // Construct and add BREAK node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1485
        appendStatement(new BreakNode(breakLine, breakToken, finish, labelName));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1486
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1487
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1488
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1489
     * ReturnStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1490
     *      return Expression? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1491
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1492
     * See 12.9
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1493
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1494
     * Parse RETURN statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1495
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1496
    private void returnStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1497
        // check for return outside function
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1498
        if (lc.getCurrentFunction().getKind() == FunctionNode.Kind.SCRIPT) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1499
            throw error(AbstractParser.message("invalid.return"));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1500
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1501
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1502
        // 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
  1503
        final int  returnLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1504
        final long returnToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1505
        // RETURN tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1506
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1507
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1508
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1509
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1510
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1511
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1512
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1513
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1514
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1515
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1516
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1517
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1518
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1519
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1520
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1521
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1522
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1523
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1524
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1525
        // 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
  1526
        appendStatement(new ReturnNode(returnLine, returnToken, finish, expression));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1527
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1528
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1529
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1530
     * YieldStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1531
     *      yield Expression? ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1532
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1533
     * JavaScript 1.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1534
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1535
     * Parse YIELD statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1536
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1537
    private void yieldStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1538
        // 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
  1539
        final int  yieldLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1540
        final long yieldToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1541
        // YIELD tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1542
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1543
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1544
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1545
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1546
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1547
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1548
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1549
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1550
        case EOL:
18625
13558072545a 8019473: Parser issues related to functions and blocks
sundar
parents: 18335
diff changeset
  1551
        case EOF:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1552
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1553
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1554
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1555
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1556
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1557
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1558
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1559
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1560
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1561
        // 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
  1562
        appendStatement(new ReturnNode(yieldLine, yieldToken, finish, expression));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1563
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1564
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1565
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1566
     * WithStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1567
     *      with ( Expression ) Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1568
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1569
     * See 12.10
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1570
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1571
     * Parse WITH statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1572
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1573
    private void withStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1574
        // 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
  1575
        final int  withLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1576
        final long withToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1577
        // WITH tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1578
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1579
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1580
        // ECMA 12.10.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1581
        if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1582
            throw error(AbstractParser.message("strict.no.with"), withToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1583
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1584
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1585
        // Get WITH expression.
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
  1586
        WithNode withNode = new WithNode(withLine, withToken, finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1587
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1588
        try {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1589
            lc.push(withNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1590
            expect(LPAREN);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1591
            withNode = withNode.setExpression(lc, expression());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1592
            expect(RPAREN);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1593
            withNode = withNode.setBody(lc, getStatement());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1594
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1595
            lc.pop(withNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1596
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1597
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1598
        appendStatement(withNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1599
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1600
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1601
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1602
     * SwitchStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1603
     *      switch ( Expression ) CaseBlock
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1604
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1605
     * CaseBlock :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1606
     *      { CaseClauses? }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1607
     *      { CaseClauses? DefaultClause CaseClauses }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1608
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1609
     * CaseClauses :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1610
     *      CaseClause
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1611
     *      CaseClauses CaseClause
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1612
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1613
     * CaseClause :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1614
     *      case Expression : StatementList?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1615
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1616
     * DefaultClause :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1617
     *      default : StatementList?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1618
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1619
     * See 12.11
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1620
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1621
     * Parse SWITCH statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1622
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1623
    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
  1624
        final int  switchLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1625
        final long switchToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1626
        // SWITCH tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1627
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1628
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1629
        // Create and add switch statement.
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
  1630
        SwitchNode switchNode = new SwitchNode(switchLine, switchToken, Token.descPosition(switchToken), null, new ArrayList<CaseNode>(), null);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1631
        lc.push(switchNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1632
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1633
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1634
            expect(LPAREN);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1635
            switchNode = switchNode.setExpression(lc, expression());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1636
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1637
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1638
            expect(LBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1639
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1640
            // Prepare to accumulate cases.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1641
            final List<CaseNode> cases = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1642
            CaseNode defaultCase = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1643
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1644
            while (type != RBRACE) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1645
                // Prepare for next case.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1646
                Expression caseExpression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1647
                final long caseToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1648
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1649
                switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1650
                case CASE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1651
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1652
                    caseExpression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1653
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1654
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1655
                case DEFAULT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1656
                    if (defaultCase != null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1657
                        throw error(AbstractParser.message("duplicate.default.in.switch"));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1658
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1659
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1660
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1661
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1662
                default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1663
                    // Force an error.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1664
                    expect(CASE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1665
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1666
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1667
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1668
                expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1669
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1670
                // Get CASE body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1671
                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
  1672
                final CaseNode caseNode = new CaseNode(caseToken, finish, caseExpression, statements);
16153
60de45bf54b0 8005703: Offsets miscalculated for blocks
jlaskey
parents: 16151
diff changeset
  1673
                statements.setFinish(finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1674
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1675
                if (caseExpression == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1676
                    defaultCase = caseNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1677
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1678
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1679
                cases.add(caseNode);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1680
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1681
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1682
            switchNode = switchNode.setCases(lc, cases, defaultCase);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1683
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1684
            switchNode.setFinish(finish);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1685
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1686
            appendStatement(switchNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1687
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1688
            lc.pop(switchNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1689
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1690
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1691
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1692
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1693
     * LabelledStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1694
     *      Identifier : Statement
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1695
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1696
     * See 12.12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1697
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1698
     * Parse label statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1699
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1700
    private void labelStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1701
        // Capture label token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1702
        final long labelToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1703
        // Get label ident.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1704
        final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1705
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1706
        expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1707
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1708
        if (lc.findLabel(ident.getName()) != null) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1709
            throw error(AbstractParser.message("duplicate.label", ident.getName()), labelToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1710
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1711
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1712
        LabelNode labelNode = new LabelNode(line, labelToken, finish, ident.getName(), null);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1713
        try {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1714
            lc.push(labelNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1715
            labelNode = labelNode.setBody(lc, getStatement());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1716
            labelNode.setFinish(finish);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1717
            appendStatement(labelNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1718
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1719
            assert lc.peek() instanceof LabelNode;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1720
            lc.pop(labelNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1721
        }
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
   /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1725
     * ThrowStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1726
     *      throw Expression ; // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1727
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1728
     * See 12.13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1729
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1730
     * Parse throw statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1731
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1732
    private void throwStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1733
        // 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
  1734
        final int  throwLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1735
        final long throwToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1736
        // THROW tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1737
        nextOrEOL();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1738
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1739
        Expression expression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1740
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1741
        // SEMICOLON or expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1742
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1743
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1744
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1745
        case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1746
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1747
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1748
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1749
            expression = expression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1750
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1751
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1752
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1753
        if (expression == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1754
            throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1755
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1756
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1757
        endOfLine();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1758
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1759
        appendStatement(new ThrowNode(throwLine, throwToken, finish, expression, false));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1760
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1761
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1762
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1763
     * TryStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1764
     *      try Block Catch
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1765
     *      try Block Finally
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1766
     *      try Block Catch Finally
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1767
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1768
     * Catch :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1769
     *      catch( Identifier if Expression ) Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1770
     *      catch( Identifier ) Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1771
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1772
     * Finally :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1773
     *      finally Block
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1774
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1775
     * See 12.14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1776
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1777
     * Parse TRY statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1778
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1779
    private void tryStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1780
        // 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
  1781
        final int  tryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1782
        final long tryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1783
        // TRY tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1784
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1785
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1786
        // 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
  1787
        final int startLine = line;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1788
        Block outer = newBlock();
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1789
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1790
        // Create try.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1791
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1792
        try {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1793
            final Block       tryBody     = getBlock(true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1794
            final List<Block> catchBlocks = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1795
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1796
            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
  1797
                final int  catchLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1798
                final long catchToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1799
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1800
                expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1801
                final IdentNode exception = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1802
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1803
                // ECMA 12.4.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1804
                verifyStrictIdent(exception, "catch argument");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1805
23766
a3ef17770bab 8039047: Parser accepts conditional catch clauses even when --no-syntax-extensions / -nse option is passed
sundar
parents: 23372
diff changeset
  1806
                // 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
  1807
                // 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
  1808
                // 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
  1809
                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
  1810
                if (!env._no_syntax_extensions && type == IF) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1811
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1812
                    // Get the exception condition.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1813
                    ifExpression = expression();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1814
                } else {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1815
                    ifExpression = null;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1816
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1817
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1818
                expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1819
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1820
                Block catchBlock = newBlock();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1821
                try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1822
                    // Get CATCH body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1823
                    final Block catchBody = getBlock(true);
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1824
                    final CatchNode catchNode = new CatchNode(catchLine, catchToken, finish, exception, ifExpression, catchBody, false);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1825
                    appendStatement(catchNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1826
                } finally {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1827
                    catchBlock = restoreBlock(catchBlock);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1828
                    catchBlocks.add(catchBlock);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1829
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1830
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1831
                // If unconditional catch then should to be the end.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1832
                if (ifExpression == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1833
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1834
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1835
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1836
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1837
            // Prepare to capture finally statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1838
            Block finallyStatements = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1839
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1840
            if (type == FINALLY) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1841
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1842
                finallyStatements = getBlock(true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1843
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1844
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1845
            // Need at least one catch or a finally.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1846
            if (catchBlocks.isEmpty() && finallyStatements == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1847
                throw error(AbstractParser.message("missing.catch.or.finally"), tryToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1848
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1849
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
  1850
            final TryNode tryNode = new TryNode(tryLine, tryToken, Token.descPosition(tryToken), tryBody, catchBlocks, finallyStatements);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1851
            // Add try.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1852
            assert lc.peek() == outer;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1853
            appendStatement(tryNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1854
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1855
            tryNode.setFinish(finish);
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1856
            outer.setFinish(finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1857
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1858
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1859
            outer = restoreBlock(outer);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1860
        }
16239
fbae49f786c6 8008215: break in catch clause causes java.lang.VerifyError: Inconsistent stackmap
hannesw
parents: 16237
diff changeset
  1861
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1862
        appendStatement(new BlockStatement(startLine, outer));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1863
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1864
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1865
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1866
     * DebuggerStatement :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1867
     *      debugger ;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1868
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1869
     * See 12.15
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1870
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1871
     * Parse debugger statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1872
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1873
    private void  debuggerStatement() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1874
        // 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
  1875
        final int  debuggerLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1876
        final long debuggerToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1877
        // DEBUGGER tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1878
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1879
        endOfLine();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1880
        appendStatement(new ExpressionStatement(debuggerLine, debuggerToken, finish, new RuntimeNode(debuggerToken, finish, RuntimeNode.Request.DEBUGGER, new ArrayList<Expression>())));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1881
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1882
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1883
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1884
     * PrimaryExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1885
     *      this
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1886
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1887
     *      Literal
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1888
     *      ArrayLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1889
     *      ObjectLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1890
     *      ( Expression )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1891
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1892
     *  See 11.1
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1893
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1894
     * Parse primary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1895
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1896
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1897
    @SuppressWarnings("fallthrough")
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1898
    private Expression primaryExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1899
        // 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
  1900
        final int  primaryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1901
        final long primaryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1902
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1903
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1904
        case THIS:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1905
            final String name = type.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1906
            next();
23372
09707b3e5fb0 8021350: Share script classes between threads/globals within context
hannesw
parents: 22390
diff changeset
  1907
            lc.setFlag(lc.getCurrentFunction(), FunctionNode.USES_THIS);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1908
            return new IdentNode(primaryToken, finish, name);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1909
        case IDENT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1910
            final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1911
            if (ident == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1912
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1913
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1914
            detectSpecialProperty(ident);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1915
            return ident;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1916
        case OCTAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1917
            if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  1918
               throw error(AbstractParser.message("strict.no.octal"), token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1919
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1920
        case STRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1921
        case ESCSTRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1922
        case DECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1923
        case HEXADECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1924
        case FLOATING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1925
        case REGEX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1926
        case XML:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1927
            return getLiteral();
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1928
        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
  1929
            return execString(primaryLine, primaryToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1930
        case FALSE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1931
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1932
            return LiteralNode.newInstance(primaryToken, finish, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1933
        case TRUE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1934
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1935
            return LiteralNode.newInstance(primaryToken, finish, true);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1936
        case NULL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1937
            next();
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  1938
            return LiteralNode.newInstance(primaryToken, finish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1939
        case LBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1940
            return arrayLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1941
        case LBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1942
            return objectLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1943
        case LPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1944
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1945
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1946
            final Expression expression = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1947
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1948
            expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1949
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1950
            return expression;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1951
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1952
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1953
            // 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
  1954
            if (lexer.scanLiteral(primaryToken, type, lineInfoReceiver)) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1955
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1956
                return getLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1957
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1958
            if (isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1959
                return getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1960
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1961
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1962
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1963
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1964
        return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1965
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1966
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1967
    /**
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1968
     * Convert execString to a call to $EXEC.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1969
     *
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1970
     * @param primaryToken Original string token.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1971
     * @return callNode to $EXEC.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1972
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1973
    CallNode execString(final int primaryLine, final long primaryToken) {
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1974
        // 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
  1975
        final IdentNode execIdent = new IdentNode(primaryToken, finish, ScriptingFunctions.EXEC_NAME);
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1976
        // Skip over EXECSTRING.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1977
        next();
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1978
        // Set up argument list for call.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1979
        // Skip beginning of edit string expression.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1980
        expect(LBRACE);
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1981
        // Add the following expression to arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  1982
        final List<Expression> arguments = Collections.singletonList(expression());
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1983
        // Skip ending of edit string expression.
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1984
        expect(RBRACE);
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1985
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  1986
        return new CallNode(primaryLine, primaryToken, finish, execIdent, arguments, false);
16211
41e031a45186 8006191: `cmd` -> exec("cmd") in script mode
jlaskey
parents: 16206
diff changeset
  1987
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1988
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1989
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1990
     * ArrayLiteral :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1991
     *      [ Elision? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1992
     *      [ ElementList ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1993
     *      [ ElementList , Elision? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1994
     *      [ expression for (LeftHandExpression in expression) ( (if ( Expression ) )? ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1995
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1996
     * ElementList : Elision? AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1997
     *      ElementList , Elision? AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1998
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  1999
     * Elision :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2000
     *      ,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2001
     *      Elision ,
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2002
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2003
     * See 12.1.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2004
     * JavaScript 1.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2005
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2006
     * Parse array literal.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2007
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2008
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2009
    private LiteralNode<Expression[]> arrayLiteral() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2010
        // Capture LBRACKET token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2011
        final long arrayToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2012
        // LBRACKET tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2013
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2014
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2015
        // Prepare to accummulating elements.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2016
        final List<Expression> elements = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2017
        // Track elisions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2018
        boolean elision = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2019
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2020
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2021
             switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2022
            case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2023
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2024
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2025
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2026
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2027
            case COMMARIGHT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2028
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2029
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2030
                // If no prior expression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2031
                if (elision) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2032
                    elements.add(null);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2033
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2034
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2035
                elision = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2036
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2037
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2038
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2039
            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
  2040
                if (!elision) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2041
                    throw error(AbstractParser.message("expected.comma", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2042
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2043
                // Add expression element.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2044
                final Expression expression = assignmentExpression(false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2045
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2046
                if (expression != null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2047
                    elements.add(expression);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2048
                } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2049
                    expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2050
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2051
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2052
                elision = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2053
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2054
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2055
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2056
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2057
        return LiteralNode.newInstance(arrayToken, finish, elements);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2058
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2059
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2060
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2061
     * ObjectLiteral :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2062
     *      { }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2063
     *      { PropertyNameAndValueList } { PropertyNameAndValueList , }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2064
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2065
     * PropertyNameAndValueList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2066
     *      PropertyAssignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2067
     *      PropertyNameAndValueList , PropertyAssignment
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2068
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2069
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2070
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2071
     * Parse an object literal.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2072
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2073
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2074
    private ObjectNode objectLiteral() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2075
        // Capture LBRACE token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2076
        final long objectToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2077
        // LBRACE tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2078
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2079
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2080
        // Object context.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2081
        // Prepare to accumulate elements.
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2082
        final List<PropertyNode> elements = new ArrayList<>();
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2083
        final Map<String, Integer> map = new HashMap<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2084
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
  2085
        // 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
  2086
        boolean commaSeen = true;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2087
loop:
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2088
        while (true) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2089
            switch (type) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2090
                case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2091
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2092
                    break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2093
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2094
                case COMMARIGHT:
18629
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2095
                    if (commaSeen) {
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2096
                        throw error(AbstractParser.message("expected.property.id", type.getNameOrType()));
6b0b6aab4280 8019508: Comma handling in object literal parsing is wrong
sundar
parents: 18625
diff changeset
  2097
                    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2098
                    next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2099
                    commaSeen = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2100
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2101
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2102
                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
  2103
                    if (!commaSeen) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2104
                        throw error(AbstractParser.message("expected.comma", type.getNameOrType()));
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2105
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2106
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2107
                    commaSeen = false;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2108
                    // Get and add the next property.
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2109
                    final PropertyNode property = propertyAssignment();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2110
                    final String key = property.getKeyName();
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2111
                    final Integer existing = map.get(key);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2112
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2113
                    if (existing == null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2114
                        map.put(key, elements.size());
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2115
                        elements.add(property);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2116
                        break;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2117
                    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2118
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2119
                    final PropertyNode existingProperty = elements.get(existing);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2120
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
  2121
                    // 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
  2122
                    // point # 4 on property assignment production
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2123
                    final Expression   value  = property.getValue();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2124
                    final FunctionNode getter = property.getGetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2125
                    final FunctionNode setter = property.getSetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2126
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2127
                    final Expression   prevValue  = existingProperty.getValue();
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2128
                    final FunctionNode prevGetter = existingProperty.getGetter();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2129
                    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
  2130
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
  2131
                    // 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
  2132
                    if (isStrictMode && value != null && prevValue != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2133
                        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
  2134
                    }
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
  2135
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
  2136
                    final boolean isPrevAccessor = prevGetter != null || prevSetter != null;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2137
                    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
  2138
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
  2139
                    // 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
  2140
                    if (prevValue != null && isAccessor) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2141
                        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
  2142
                    }
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
  2143
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
                    // 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
  2145
                    if (isPrevAccessor && value != null) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2146
                        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
  2147
                    }
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
  2148
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
  2149
                    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
  2150
                        if (getter != null && prevGetter != null ||
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2151
                                setter != null && prevSetter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2152
                            throw error(AbstractParser.message("property.redefinition", key), property.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2153
                        }
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
  2154
                    }
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
  2155
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
  2156
                    if (value != null) {
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2157
                        elements.add(property);
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2158
                    } else if (getter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2159
                        elements.set(existing, existingProperty.setGetter(getter));
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2160
                    } else if (setter != null) {
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2161
                        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
  2162
                    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2163
                    break;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2164
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2165
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2166
18877
6d75ba520886 8020354: Object literal property initialization is not done in source order
hannesw
parents: 18870
diff changeset
  2167
        return new ObjectNode(objectToken, finish, elements);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2168
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2169
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2170
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2171
     * PropertyName :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2172
     *      IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2173
     *      StringLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2174
     *      NumericLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2175
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2176
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2177
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2178
     * @return PropertyName node
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2179
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2180
    @SuppressWarnings("fallthrough")
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2181
    private PropertyKey propertyName() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2182
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2183
        case IDENT:
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2184
            return getIdent().setIsPropertyName();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2185
        case OCTAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2186
            if (isStrictMode) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2187
                throw error(AbstractParser.message("strict.no.octal"), token);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2188
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2189
        case STRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2190
        case ESCSTRING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2191
        case DECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2192
        case HEXADECIMAL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2193
        case FLOATING:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2194
            return getLiteral();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2195
        default:
19883
aae0838ac6ee 8024255: When a keyword is used as object property name, the property can not be deleted
sundar
parents: 19472
diff changeset
  2196
            return getIdentifierName().setIsPropertyName();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2197
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2198
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2199
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2200
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2201
     * PropertyAssignment :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2202
     *      PropertyName : AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2203
     *      get PropertyName ( ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2204
     *      set PropertyName ( PropertySetParameterList ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2205
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2206
     * PropertySetParameterList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2207
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2208
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2209
     * PropertyName :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2210
     *      IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2211
     *      StringLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2212
     *      NumericLiteral
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2213
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2214
     * See 11.1.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2215
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2216
     * Parse an object literal property.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2217
     * @return Property or reference node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2218
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2219
    private PropertyNode propertyAssignment() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2220
        // Capture firstToken.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2221
        final long propertyToken = token;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2222
        final int  functionLine  = line;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2223
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2224
        PropertyKey propertyName;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2225
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2226
        if (type == IDENT) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2227
            // Get IDENT.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2228
            final String ident = (String)expectValue(IDENT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2229
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2230
            if (type != COLON) {
20938
e92d8249f60c 8026302: source representation of getter and setter methods is wrong
sundar
parents: 20934
diff changeset
  2231
                final long getSetToken = propertyToken;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2232
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2233
                switch (ident) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2234
                case "get":
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2235
                    final PropertyFunction getter = propertyGetterFunction(getSetToken, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2236
                    return new PropertyNode(propertyToken, finish, getter.ident, null, getter.functionNode, null);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2237
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2238
                case "set":
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2239
                    final PropertyFunction setter = propertySetterFunction(getSetToken, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2240
                    return new PropertyNode(propertyToken, finish, setter.ident, null, null, setter.functionNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2241
                default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2242
                    break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2243
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2244
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2245
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2246
            propertyName =  new IdentNode(propertyToken, finish, ident).setIsPropertyName();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2247
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2248
            propertyName = propertyName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2249
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2250
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2251
        expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2252
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2253
        defaultNames.push(propertyName);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2254
        try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2255
            return new PropertyNode(propertyToken, finish, propertyName, assignmentExpression(false), null, null);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2256
        } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2257
            defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2258
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2259
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2260
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2261
    private PropertyFunction propertyGetterFunction(final long getSetToken, final int functionLine) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2262
        final PropertyKey getIdent = propertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2263
        final String getterName = getIdent.getPropertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2264
        final IdentNode getNameNode = new IdentNode(((Node)getIdent).getToken(), finish, NameCodec.encode("get " + getterName));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2265
        expect(LPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2266
        expect(RPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2267
        final FunctionNode functionNode = functionBody(getSetToken, getNameNode, new ArrayList<IdentNode>(), FunctionNode.Kind.GETTER, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2268
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2269
        return new PropertyFunction(getIdent, functionNode);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2270
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2271
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2272
    private PropertyFunction propertySetterFunction(final long getSetToken, final int functionLine) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2273
        final PropertyKey setIdent = propertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2274
        final String setterName = setIdent.getPropertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2275
        final IdentNode setNameNode = new IdentNode(((Node)setIdent).getToken(), finish, NameCodec.encode("set " + setterName));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2276
        expect(LPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2277
        // be sloppy and allow missing setter parameter even though
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2278
        // spec does not permit it!
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2279
        final IdentNode argIdent;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2280
        if (type == IDENT || isNonStrictModeIdent()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2281
            argIdent = getIdent();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2282
            verifyStrictIdent(argIdent, "setter argument");
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2283
        } else {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2284
            argIdent = null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2285
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2286
        expect(RPAREN);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2287
        final List<IdentNode> parameters = new ArrayList<>();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2288
        if (argIdent != null) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2289
            parameters.add(argIdent);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2290
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2291
        final FunctionNode functionNode = functionBody(getSetToken, setNameNode, parameters, FunctionNode.Kind.SETTER, functionLine);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2292
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2293
        return new PropertyFunction(setIdent, functionNode);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2294
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2295
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2296
    private static class PropertyFunction {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2297
        final PropertyKey ident;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2298
        final FunctionNode functionNode;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2299
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2300
        PropertyFunction(final PropertyKey ident, final FunctionNode function) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2301
            this.ident = ident;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2302
            this.functionNode = function;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2303
        }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2304
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2305
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2306
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2307
     * LeftHandSideExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2308
     *      NewExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2309
     *      CallExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2310
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2311
     * CallExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2312
     *      MemberExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2313
     *      CallExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2314
     *      CallExpression [ Expression ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2315
     *      CallExpression . IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2316
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2317
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2318
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2319
     * Parse left hand side expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2320
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2321
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2322
    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
  2323
        int  callLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2324
        long callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2325
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2326
        Expression lhs = memberExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2327
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2328
        if (type == LPAREN) {
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2329
            final List<Expression> arguments = optimizeList(argumentList());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2330
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2331
            // Catch special functions.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2332
            if (lhs instanceof IdentNode) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2333
                detectSpecialFunction((IdentNode)lhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2334
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2335
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2336
            lhs = new CallNode(callLine, callToken, finish, lhs, arguments, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2337
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2338
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2339
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2340
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2341
            // 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
  2342
            callLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2343
            callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2344
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2345
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2346
            case LPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2347
                // Get NEW or FUNCTION arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2348
                final List<Expression> arguments = optimizeList(argumentList());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2349
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2350
                // Create call node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2351
                lhs = new CallNode(callLine, callToken, finish, lhs, arguments, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2352
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2353
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2354
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2355
            case LBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2356
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2357
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2358
                // Get array index.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2359
                final Expression rhs = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2360
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2361
                expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2362
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2363
                // Create indexing node.
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2364
                lhs = new IndexNode(callToken, finish, lhs, rhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2365
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2366
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2367
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2368
            case PERIOD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2369
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2370
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2371
                final IdentNode property = getIdentifierName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2372
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2373
                // Create property access node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2374
                lhs = new AccessNode(callToken, finish, lhs, property.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2375
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2376
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2377
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2378
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2379
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2380
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2381
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2382
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2383
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2384
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2385
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2386
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2387
     * NewExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2388
     *      MemberExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2389
     *      new NewExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2390
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2391
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2392
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2393
     * Parse new expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2394
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2395
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2396
    private Expression newExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2397
        final long newToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2398
        // NEW is tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2399
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2400
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2401
        // 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
  2402
        final int  callLine    = line;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2403
        final Expression constructor = memberExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2404
        if (constructor == null) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2405
            return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2406
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2407
        // Get arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2408
        ArrayList<Expression> arguments;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2409
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2410
        // Allow for missing arguments.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2411
        if (type == LPAREN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2412
            arguments = argumentList();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2413
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2414
            arguments = new ArrayList<>();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2415
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2416
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2417
        // 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
  2418
        // syntax:
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2419
        //
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2420
        //     var r = new java.lang.Runnable() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2421
        //         run: function() { println("run"); }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2422
        //     };
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2423
        //
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2424
        // The object literal following the "new Constructor()" expresssion
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2425
        // 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
  2426
        if (!env._no_syntax_extensions && type == LBRACE) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2427
            arguments.add(objectLiteral());
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2428
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2429
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2430
        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
  2431
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2432
        return new UnaryNode(newToken, callNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2433
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2434
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2435
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2436
     * MemberExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2437
     *      PrimaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2438
     *      FunctionExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2439
     *      MemberExpression [ Expression ]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2440
     *      MemberExpression . IdentifierName
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2441
     *      new MemberExpression Arguments
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2442
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2443
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2444
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2445
     * Parse member expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2446
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2447
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2448
    private Expression memberExpression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2449
        // Prepare to build operation.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2450
        Expression lhs;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2451
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2452
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2453
        case NEW:
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2454
            // Get new expression.
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2455
            lhs = newExpression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2456
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2457
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2458
        case FUNCTION:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2459
            // Get function expression.
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2460
            lhs = functionExpression(false, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2461
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2462
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2463
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2464
            // Get primary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2465
            lhs = primaryExpression();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2466
            break;
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
loop:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2470
        while (true) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2471
            // Capture token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2472
            final long callToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2473
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2474
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2475
            case LBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2476
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2477
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2478
                // Get array index.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2479
                final Expression index = expression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2480
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2481
                expect(RBRACKET);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2482
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2483
                // Create indexing node.
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2484
                lhs = new IndexNode(callToken, finish, lhs, index);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2485
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2486
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2487
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2488
            case PERIOD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2489
                if (lhs == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2490
                    throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2491
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2492
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2493
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2494
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2495
                final IdentNode property = getIdentifierName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2496
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2497
                // Create property access node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2498
                lhs = new AccessNode(callToken, finish, lhs, property.getName());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2499
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2500
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2501
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2502
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2503
                break loop;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2504
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2505
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2506
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2507
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2508
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2509
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2510
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2511
     * Arguments :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2512
     *      ( )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2513
     *      ( ArgumentList )
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2514
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2515
     * ArgumentList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2516
     *      AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2517
     *      ArgumentList , AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2518
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2519
     * See 11.2
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2520
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2521
     * Parse function call arguments.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2522
     * @return Argument list.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2523
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2524
    private ArrayList<Expression> argumentList() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2525
        // Prepare to accumulate list of arguments.
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2526
        final ArrayList<Expression> nodeList = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2527
        // LPAREN tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2528
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2529
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2530
        // Track commas.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2531
        boolean first = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2532
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2533
        while (type != RPAREN) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2534
            // Comma prior to every argument except the first.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2535
            if (!first) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2536
                expect(COMMARIGHT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2537
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2538
                first = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2539
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2540
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2541
            // Get argument expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2542
            nodeList.add(assignmentExpression(false));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2543
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2544
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2545
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2546
        return nodeList;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2547
    }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2548
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
  2549
    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
  2550
        switch(list.size()) {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2551
            case 0: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2552
                return Collections.emptyList();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2553
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2554
            case 1: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2555
                return Collections.singletonList(list.get(0));
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2556
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2557
            default: {
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2558
                list.trimToSize();
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2559
                return list;
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2560
            }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2561
        }
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2562
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2563
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2564
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2565
     * FunctionDeclaration :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2566
     *      function Identifier ( FormalParameterList? ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2567
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2568
     * FunctionExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2569
     *      function Identifier? ( FormalParameterList? ) { FunctionBody }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2570
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2571
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2572
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2573
     * Parse function declaration.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2574
     * @param isStatement True if for is a statement.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2575
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2576
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2577
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2578
    private Expression functionExpression(final boolean isStatement, final boolean topLevel) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2579
        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
  2580
        final int  functionLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2581
        // FUNCTION is tested in caller.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2582
        next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2583
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2584
        IdentNode name = null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2585
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2586
        if (type == IDENT || isNonStrictModeIdent()) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2587
            name = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2588
            verifyStrictIdent(name, "function name");
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2589
        } else if (isStatement) {
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2590
            // Nashorn extension: anonymous function statements
18335
1b5fdae617cf 8016550: nashorn.option.no.syntax.extensions has the wrong default
sundar
parents: 17981
diff changeset
  2591
            if (env._no_syntax_extensions) {
16196
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2592
                expect(IDENT);
58f6f046bb5e 8006983: Introduce a command line option to switch off syntactic extensions of nashorn
sundar
parents: 16191
diff changeset
  2593
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2594
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2595
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2596
        // name is null, generate anonymous name
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2597
        boolean isAnonymous = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2598
        if (name == null) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2599
            final String tmpName = getDefaultValidFunctionName(functionLine);
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2600
            name = new IdentNode(functionToken, Token.descPosition(functionToken), tmpName);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2601
            isAnonymous = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2602
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2603
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2604
        expect(LPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2605
        final List<IdentNode> parameters = formalParameterList();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2606
        expect(RPAREN);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2607
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2608
        FunctionNode functionNode = functionBody(functionToken, name, parameters, FunctionNode.Kind.NORMAL, functionLine);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2609
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2610
        if (isStatement) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2611
            if (topLevel) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2612
                functionNode = functionNode.setFlag(lc, FunctionNode.IS_DECLARED);
17257
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2613
            } else if (isStrictMode) {
a2232050cd8f 8008814: Configurable ignore/warning/error behavior for function declaration as statement
attila
parents: 17255
diff changeset
  2614
                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
  2615
            } 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
  2616
                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
  2617
            } 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
  2618
                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
  2619
            }
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2620
            if (isArguments(name)) {
17249
a2014831ae7a 8013325: function named 'arguments' should set DEFINES_ARGUMENTS flag in its parent, not itself
attila
parents: 17233
diff changeset
  2621
                lc.setFlag(lc.getCurrentFunction(), FunctionNode.DEFINES_ARGUMENTS);
16206
83069fa0935b 8006529: Methods always get callee - it should be conditional
attila
parents: 16201
diff changeset
  2622
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2623
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2624
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2625
        if (isAnonymous) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2626
            functionNode = functionNode.setFlag(lc, FunctionNode.IS_ANONYMOUS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2627
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2628
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2629
        final int arity = parameters.size();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2630
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2631
        final boolean strict = functionNode.isStrict();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2632
        if (arity > 1) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2633
            final HashSet<String> parametersSet = new HashSet<>(arity);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2634
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2635
            for (int i = arity - 1; i >= 0; i--) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2636
                final IdentNode parameter = parameters.get(i);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2637
                String parameterName = parameter.getName();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2638
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2639
                if (isArguments(parameterName)) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2640
                    functionNode = functionNode.setFlag(lc, FunctionNode.DEFINES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2641
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2642
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2643
                if (parametersSet.contains(parameterName)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2644
                    // redefinition of parameter name
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2645
                    if (strict) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2646
                        throw error(AbstractParser.message("strict.param.redefinition", parameterName), parameter.getToken());
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2647
                    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2648
                    // rename in non-strict mode
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2649
                    parameterName = functionNode.uniqueName(parameterName);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2650
                    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
  2651
                    parameters.set(i, new IdentNode(parameterToken, Token.descPosition(parameterToken), functionNode.uniqueName(parameterName)));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2652
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2653
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2654
                parametersSet.add(parameterName);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2655
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2656
        } else if (arity == 1) {
19898
58c39862aa3f 8024846: keep separate internal arguments variable
attila
parents: 19883
diff changeset
  2657
            if (isArguments(parameters.get(0))) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2658
                functionNode = functionNode.setFlag(lc, FunctionNode.DEFINES_ARGUMENTS);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2659
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2660
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2661
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2662
        if (isStatement) {
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 VarNode varNode = new VarNode(functionLine, functionToken, finish, name, functionNode, VarNode.IS_STATEMENT);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2664
            if (topLevel) {
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2665
                functionDeclarations.add(varNode);
16191
7dd981da8e11 8006755: Functions inside with statements dont get correct scope
sundar
parents: 16187
diff changeset
  2666
            } else {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2667
                appendStatement(varNode);
16191
7dd981da8e11 8006755: Functions inside with statements dont get correct scope
sundar
parents: 16187
diff changeset
  2668
            }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2669
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2670
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2671
        return functionNode;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2672
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2673
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2674
    private String getDefaultValidFunctionName(final int functionLine) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2675
        final String defaultFunctionName = getDefaultFunctionName();
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
  2676
        return isValidIdentifier(defaultFunctionName) ? defaultFunctionName : ANON_FUNCTION_PREFIX.symbolName() + functionLine;
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2677
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2678
24744
5290da85fc3d 8038426: Move all loggers from process wide scope into Global scope
lagergren
parents: 24727
diff changeset
  2679
    private static boolean isValidIdentifier(final String name) {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2680
        if(name == null || name.isEmpty()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2681
            return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2682
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2683
        if(!Character.isJavaIdentifierStart(name.charAt(0))) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2684
            return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2685
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2686
        for(int i = 1; i < name.length(); ++i) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2687
            if(!Character.isJavaIdentifierPart(name.charAt(i))) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2688
                return false;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2689
            }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2690
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2691
        return true;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2692
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2693
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2694
    private String getDefaultFunctionName() {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2695
        if(!defaultNames.isEmpty()) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2696
            final Object nameExpr = defaultNames.peek();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2697
            if(nameExpr instanceof PropertyKey) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2698
                markDefaultNameUsed();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2699
                return ((PropertyKey)nameExpr).getPropertyName();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2700
            } else if(nameExpr instanceof AccessNode) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2701
                markDefaultNameUsed();
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2702
                return ((AccessNode)nameExpr).getProperty();
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2703
            }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2704
        }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2705
        return null;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2706
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2707
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2708
    private void markDefaultNameUsed() {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2709
        defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2710
        // 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
  2711
        // from. Can't be null
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2712
        defaultNames.push("");
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2713
    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2714
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2715
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2716
     * FormalParameterList :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2717
     *      Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2718
     *      FormalParameterList , Identifier
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2719
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2720
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2721
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2722
     * Parse function parameter list.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2723
     * @return List of parameter nodes.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2724
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2725
    private List<IdentNode> formalParameterList() {
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2726
        return formalParameterList(RPAREN);
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2727
    }
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2728
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2729
    /**
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2730
     * 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
  2731
     * token type expected is passed as argument to this method.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2732
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2733
     * FormalParameterList :
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2734
     *      Identifier
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2735
     *      FormalParameterList , Identifier
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2736
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2737
     * See 13
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2738
     *
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2739
     * Parse function parameter list.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2740
     * @return List of parameter nodes.
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2741
     */
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2742
    private List<IdentNode> formalParameterList(final TokenType endType) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2743
        // Prepare to gather parameters.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2744
        final ArrayList<IdentNode> parameters = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2745
        // Track commas.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2746
        boolean first = true;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2747
17973
d220c8157f25 8015345: Function("}),print('test'),({") should throw SyntaxError
sundar
parents: 17745
diff changeset
  2748
        while (type != endType) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2749
            // Comma prior to every argument except the first.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2750
            if (!first) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2751
                expect(COMMARIGHT);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2752
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2753
                first = false;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2754
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2755
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2756
            // Get and add parameter.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2757
            final IdentNode ident = getIdent();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2758
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2759
            // ECMA 13.1 strict mode restrictions
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2760
            verifyStrictIdent(ident, "function parameter");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2761
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2762
            parameters.add(ident);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2763
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2764
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  2765
        parameters.trimToSize();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2766
        return parameters;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2767
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2768
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2769
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2770
     * FunctionBody :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2771
     *      SourceElements?
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2772
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2773
     * See 13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2774
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2775
     * Parse function body.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2776
     * @return function node (body.)
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2777
     */
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2778
    private FunctionNode functionBody(final long firstToken, final IdentNode ident, final List<IdentNode> parameters, final FunctionNode.Kind kind, final int functionLine) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2779
        FunctionNode functionNode = null;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2780
        long lastToken = 0L;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2781
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2782
        try {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2783
            // Create a new function block.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2784
            functionNode = newFunctionNode(firstToken, ident, parameters, kind, functionLine);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2785
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2786
            // Nashorn extension: expression closures
16262
75513555e603 8008731: Separate configuration environment (options, error/output writer etc.) from Context
sundar
parents: 16252
diff changeset
  2787
            if (!env._no_syntax_extensions && type != LBRACE) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2788
                /*
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2789
                 * Example:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2790
                 *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2791
                 * function square(x) x * x;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2792
                 * print(square(3));
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2793
                 */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2794
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2795
                // just expression as function body
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2796
                final Expression expr = assignmentExpression(true);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2797
                lastToken = previousToken;
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2798
                assert lc.getCurrentBlock() == lc.getFunctionBody(functionNode);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2799
                // EOL uses length field to store the line number
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2800
                final int lastFinish = Token.descPosition(lastToken) + (Token.descType(lastToken) == EOL ? 0 : Token.descLength(lastToken));
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2801
                final ReturnNode returnNode = new ReturnNode(functionNode.getLineNumber(), expr.getToken(), lastFinish, expr);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2802
                appendStatement(returnNode);
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2803
                functionNode.setFinish(lastFinish);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2804
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2805
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2806
                expect(LBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2807
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2808
                // Gather the function elements.
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
  2809
                final List<Statement> prevFunctionDecls = functionDeclarations;
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2810
                functionDeclarations = new ArrayList<>();
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2811
                try {
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  2812
                    sourceElements(false);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2813
                    addFunctionDeclarations(functionNode);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2814
                } finally {
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2815
                    functionDeclarations = prevFunctionDecls;
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  2816
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2817
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2818
                lastToken = token;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2819
                expect(RBRACE);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2820
                functionNode.setFinish(finish);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2821
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2822
        } finally {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2823
            functionNode = restoreFunctionNode(functionNode, lastToken);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2824
        }
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2825
        printAST(functionNode);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2826
        return functionNode;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2827
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2828
26065
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2829
    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
  2830
        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
  2831
            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
  2832
        }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2833
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2834
        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
  2835
            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
  2836
        }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2837
    }
d15adb218527 8055107: Extension directives to turn on callsite profiling, tracing, AST print and other debug features locally
sundar
parents: 26055
diff changeset
  2838
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2839
    private void addFunctionDeclarations(final FunctionNode functionNode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2840
        assert lc.peek() == lc.getFunctionBody(functionNode);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2841
        VarNode lastDecl = null;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2842
        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
  2843
            Statement decl = functionDeclarations.get(i);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2844
            if (lastDecl == null && decl instanceof VarNode) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2845
                decl = lastDecl = ((VarNode)decl).setFlag(VarNode.IS_LAST_FUNCTION_DECLARATION);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2846
                lc.setFlag(functionNode, FunctionNode.HAS_FUNCTION_DECLARATIONS);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2847
            }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2848
            prependStatement(decl);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2849
        }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2850
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2851
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2852
    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
  2853
        if (earlyError) {
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2854
            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
  2855
        }
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2856
        final ArrayList<Expression> args = new ArrayList<>();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2857
        args.add(lhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2858
        if (rhs == null) {
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2859
            args.add(LiteralNode.newInstance(lhs.getToken(), lhs.getFinish()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2860
        } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2861
            args.add(rhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2862
        }
17523
cb4a7c901e0d 8013913: Removed Source field from all nodes except FunctionNode in order to save footprint
lagergren
parents: 17518
diff changeset
  2863
        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
  2864
        return new RuntimeNode(lhs.getToken(), lhs.getFinish(), RuntimeNode.Request.REFERENCE_ERROR, args);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2865
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2866
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2867
    /*
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2868
     * parse LHS [a, b, ..., c].
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2869
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2870
     * JavaScript 1.8.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2871
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2872
    //private Node destructureExpression() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2873
    //    return null;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2874
    //}
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2875
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2876
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2877
     * PostfixExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2878
     *      LeftHandSideExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2879
     *      LeftHandSideExpression ++ // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2880
     *      LeftHandSideExpression -- // [no LineTerminator here]
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2881
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2882
     * See 11.3
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2883
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2884
     * UnaryExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2885
     *      PostfixExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2886
     *      delete UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2887
     *      Node UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2888
     *      typeof UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2889
     *      ++ UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2890
     *      -- UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2891
     *      + UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2892
     *      - UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2893
     *      ~ UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2894
     *      ! UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2895
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2896
     * See 11.4
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2897
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2898
     * Parse unary expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2899
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2900
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2901
    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
  2902
        final int  unaryLine  = line;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2903
        final long unaryToken = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2904
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2905
        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
  2906
        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
  2907
            next();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2908
            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
  2909
            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
  2910
                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
  2911
            }
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2912
            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
  2913
            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
  2914
        }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2915
        case VOID:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2916
        case TYPEOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2917
        case ADD:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2918
        case SUB:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2919
        case BIT_NOT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2920
        case NOT:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2921
            next();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2922
            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
  2923
            return new UnaryNode(unaryToken, expr);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2924
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2925
        case INCPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2926
        case DECPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2927
            final TokenType opType = type;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2928
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2929
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2930
            final Expression lhs = leftHandSideExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2931
            // ++, -- without operand..
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2932
            if (lhs == null) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2933
                throw error(AbstractParser.message("expected.lvalue", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2934
            }
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2935
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2936
            if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2937
                  lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2938
                  lhs instanceof IdentNode)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2939
                return referenceError(lhs, null, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2940
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2941
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2942
            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
  2943
                if (!checkIdentLValue((IdentNode)lhs)) {
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2944
                    return referenceError(lhs, null, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2945
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2946
                verifyStrictIdent((IdentNode)lhs, "operand for " + opType.getName() + " operator");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2947
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2948
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2949
            return incDecExpression(unaryToken, opType, lhs, false);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2950
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2951
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2952
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2953
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2954
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2955
        Expression expression = leftHandSideExpression();
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2956
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2957
        if (last != EOL) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2958
            switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2959
            case INCPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2960
            case DECPREFIX:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2961
                final TokenType opType = type;
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  2962
                final Expression lhs = expression;
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2963
                // ++, -- without operand..
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2964
                if (lhs == null) {
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2965
                    throw error(AbstractParser.message("expected.lvalue", type.getNameOrType()));
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2966
                }
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2967
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2968
                if (!(lhs instanceof AccessNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2969
                   lhs instanceof IndexNode ||
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2970
                   lhs instanceof IdentNode)) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2971
                    next();
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2972
                    return referenceError(lhs, null, env._early_lvalue_error);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2973
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2974
                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
  2975
                    if (!checkIdentLValue((IdentNode)lhs)) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2976
                        next();
18632
93017277615e 8019553: NPE on illegal l-value for increment and decrement
sundar
parents: 18629
diff changeset
  2977
                        return referenceError(lhs, null, false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2978
                    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2979
                    verifyStrictIdent((IdentNode)lhs, "operand for " + opType.getName() + " operator");
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2980
                }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2981
                expression = incDecExpression(token, type, expression, true);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2982
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2983
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2984
            default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2985
                break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2986
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2987
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2988
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2989
        if (expression == null) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  2990
            throw error(AbstractParser.message("expected.operand", type.getNameOrType()));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2991
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2992
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2993
        return expression;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2994
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2995
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2996
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2997
     * MultiplicativeExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2998
     *      UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  2999
     *      MultiplicativeExpression * UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3000
     *      MultiplicativeExpression / UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3001
     *      MultiplicativeExpression % UnaryExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3002
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3003
     * See 11.5
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3004
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3005
     * AdditiveExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3006
     *      MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3007
     *      AdditiveExpression + MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3008
     *      AdditiveExpression - MultiplicativeExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3009
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3010
     * See 11.6
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3011
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3012
     * ShiftExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3013
     *      AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3014
     *      ShiftExpression << AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3015
     *      ShiftExpression >> AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3016
     *      ShiftExpression >>> AdditiveExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3017
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3018
     * See 11.7
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3019
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3020
     * RelationalExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3021
     *      ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3022
     *      RelationalExpression < ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3023
     *      RelationalExpression > ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3024
     *      RelationalExpression <= ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3025
     *      RelationalExpression >= ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3026
     *      RelationalExpression instanceof ShiftExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3027
     *      RelationalExpression in ShiftExpression // if !noIf
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3028
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3029
     * See 11.8
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3030
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3031
     *      RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3032
     *      EqualityExpression == RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3033
     *      EqualityExpression != RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3034
     *      EqualityExpression === RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3035
     *      EqualityExpression !== RelationalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3036
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3037
     * See 11.9
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3038
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3039
     * BitwiseANDExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3040
     *      EqualityExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3041
     *      BitwiseANDExpression & EqualityExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3042
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3043
     * BitwiseXORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3044
     *      BitwiseANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3045
     *      BitwiseXORExpression ^ BitwiseANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3046
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3047
     * BitwiseORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3048
     *      BitwiseXORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3049
     *      BitwiseORExpression | BitwiseXORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3050
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3051
     * See 11.10
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3052
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3053
     * LogicalANDExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3054
     *      BitwiseORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3055
     *      LogicalANDExpression && BitwiseORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3056
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3057
     * LogicalORExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3058
     *      LogicalANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3059
     *      LogicalORExpression || LogicalANDExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3060
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3061
     * See 11.11
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3062
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3063
     * ConditionalExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3064
     *      LogicalORExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3065
     *      LogicalORExpression ? AssignmentExpression : AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3066
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3067
     * See 11.12
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3068
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3069
     * AssignmentExpression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3070
     *      ConditionalExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3071
     *      LeftHandSideExpression AssignmentOperator AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3072
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3073
     * AssignmentOperator :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3074
     *      = *= /= %= += -= <<= >>= >>>= &= ^= |=
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3075
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3076
     * See 11.13
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3077
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3078
     * Expression :
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3079
     *      AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3080
     *      Expression , AssignmentExpression
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3081
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3082
     * See 11.14
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3083
     *
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3084
     * Parse expression.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3085
     * @return Expression node.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3086
     */
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3087
    private Expression expression() {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3088
        // TODO - Destructuring array.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3089
        // Include commas in expression parsing.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3090
        return expression(unaryExpression(), COMMARIGHT.getPrecedence(), false);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3091
    }
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3092
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3093
    private JoinPredecessorExpression joinPredecessorExpression() {
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3094
        return new JoinPredecessorExpression(expression());
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3095
    }
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3096
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3097
    private Expression expression(final Expression exprLhs, final int minPrecedence, final boolean noIn) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3098
        // Get the precedence of the next operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3099
        int precedence = type.getPrecedence();
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3100
        Expression lhs = exprLhs;
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3101
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3102
        // While greater precedence.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3103
        while (type.isOperator(noIn) && precedence >= minPrecedence) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3104
            // Capture the operator token.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3105
            final long op = token;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3106
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3107
            if (type == TERNARY) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3108
                // Skip operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3109
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3110
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3111
                // Pass expression. Middle expression of a conditional expression can be a "in"
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3112
                // expression - even in the contexts where "in" is not permitted.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3113
                final Expression trueExpr = expression(unaryExpression(), ASSIGN.getPrecedence(), false);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3114
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3115
                expect(COLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3116
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3117
                // Fail expression.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3118
                final Expression falseExpr = expression(unaryExpression(), ASSIGN.getPrecedence(), noIn);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3119
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3120
                // Build up node.
24751
ccbd9cd3f720 8042118: Separate types from symbols
attila
parents: 24745
diff changeset
  3121
                lhs = new TernaryNode(op, lhs, new JoinPredecessorExpression(trueExpr), new JoinPredecessorExpression(falseExpr));
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3122
            } else {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3123
                // Skip operator.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3124
                next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3125
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3126
                 // Get the next primary expression.
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3127
                Expression rhs;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3128
                final boolean isAssign = Token.descType(op) == ASSIGN;
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3129
                if(isAssign) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3130
                    defaultNames.push(lhs);
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3131
                }
24719
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3132
                try {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3133
                    rhs = unaryExpression();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3134
                    // Get precedence of next operator.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3135
                    int nextPrecedence = type.getPrecedence();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3136
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3137
                    // Subtask greater precedence.
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3138
                    while (type.isOperator(noIn) &&
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3139
                           (nextPrecedence > precedence ||
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3140
                           nextPrecedence == precedence && !type.isLeftAssociative())) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3141
                        rhs = expression(rhs, nextPrecedence, noIn);
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3142
                        nextPrecedence = type.getPrecedence();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3143
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3144
                } finally {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3145
                    if(isAssign) {
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3146
                        defaultNames.pop();
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3147
                    }
f726e9d67629 8035820: Optimistic recompilation
attila
parents: 22390
diff changeset
  3148
                }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3149
                lhs = verifyAssignment(op, lhs, rhs);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3150
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3151
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3152
            precedence = type.getPrecedence();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3153
        }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3154
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3155
        return lhs;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3156
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3157
18867
bc91e3fcc5ba 8013925: Remove symbol fields from nodes that don't need them
attila
parents: 18853
diff changeset
  3158
    private Expression assignmentExpression(final boolean noIn) {
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3159
        // TODO - Handle decompose.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3160
        // Exclude commas in expression parsing.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3161
        return expression(unaryExpression(), ASSIGN.getPrecedence(), noIn);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3162
    }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3163
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3164
    /**
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3165
     * Parse an end of line.
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3166
     */
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3167
    private void endOfLine() {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3168
        switch (type) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3169
        case SEMICOLON:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3170
        case EOL:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3171
            next();
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3172
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3173
        case RPAREN:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3174
        case RBRACKET:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3175
        case RBRACE:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3176
        case EOF:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3177
            break;
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3178
        default:
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3179
            if (last != EOL) {
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3180
                expect(SEMICOLON);
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3181
            }
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3182
            break;
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
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3186
    @Override
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3187
    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
  3188
        return "'JavaScript Parsing'";
16252
3bfe9b68a0fa 8008648: Lazy JIT scope and callee semantics bugfixes. Broke out wallclock timer.
lagergren
parents: 16245
diff changeset
  3189
    }
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3190
17255
aa61d23e36e5 8013419: Streamline handling of with and eval
attila
parents: 17249
diff changeset
  3191
    private static void markEval(final LexicalContext lc) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3192
        final Iterator<FunctionNode> iter = lc.getFunctions();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3193
        boolean flaggedCurrentFn = false;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3194
        while (iter.hasNext()) {
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3195
            final FunctionNode fn = iter.next();
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3196
            if (!flaggedCurrentFn) {
17255
aa61d23e36e5 8013419: Streamline handling of with and eval
attila
parents: 17249
diff changeset
  3197
                lc.setFlag(fn, FunctionNode.HAS_EVAL);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3198
                flaggedCurrentFn = true;
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3199
            } else {
17255
aa61d23e36e5 8013419: Streamline handling of with and eval
attila
parents: 17249
diff changeset
  3200
                lc.setFlag(fn, FunctionNode.HAS_NESTED_EVAL);
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3201
            }
18853
25ba8264b427 8019819: scope symbol didn't get a slot in certain cases
attila
parents: 18852
diff changeset
  3202
            lc.setBlockNeedsScope(lc.getFunctionBody(fn));
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3203
        }
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3204
    }
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3205
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
  3206
    private void prependStatement(final Statement statement) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3207
        lc.prependStatement(statement);
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3208
    }
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3209
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
  3210
    private void appendStatement(final Statement statement) {
17233
72ccf78a8216 8010701: Immutable nodes - final iteration
lagergren
parents: 16530
diff changeset
  3211
        lc.appendStatement(statement);
16530
201d682e75f4 8010652: Eliminate non-child references in Block/FunctionNode, and make few node types immutable
attila
parents: 16525
diff changeset
  3212
    }
16147
e63b63819133 8005403: Open-source Nashorn
jlaskey
parents:
diff changeset
  3213
}