< prev index next >
src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/ir/FunctionNode.java
Print this page
*** 67,77 ****
/** a script function */
SCRIPT,
/** a getter, @see {@link UserAccessorProperty} */
GETTER,
/** a setter, @see {@link UserAccessorProperty} */
! SETTER
}
/** Source of entity. */
private transient final Source source;
--- 67,83 ----
/** a script function */
SCRIPT,
/** a getter, @see {@link UserAccessorProperty} */
GETTER,
/** a setter, @see {@link UserAccessorProperty} */
! SETTER,
! /** an arrow function */
! ARROW,
! /** a generator function */
! GENERATOR,
! /** a module function */
! MODULE
}
/** Source of entity. */
private transient final Source source;
*** 120,129 ****
--- 126,141 ----
private final int lineNumber;
/** Root class for function */
private final Class<?> rootClass;
+ /** The ES6 module */
+ private final Module module;
+
+ /** The debug flags */
+ private final int debugFlags;
+
/** Is anonymous function flag. */
public static final int IS_ANONYMOUS = 1 << 0;
/** Is the function created in a function declaration (as opposed to a function expression) */
public static final int IS_DECLARED = 1 << 1;
*** 185,241 ****
public static final int USES_THIS = 1 << 15;
/** Is this declared in a dynamic context */
public static final int IN_DYNAMIC_CONTEXT = 1 << 16;
- /**
- * The following flags are derived from directive comments within this function.
- * Note that even IS_STRICT is one such flag but that requires special handling.
- */
-
- /** parser, print parse tree */
- public static final int IS_PRINT_PARSE = 1 << 17;
- /** parser, print lower parse tree */
- public static final int IS_PRINT_LOWER_PARSE = 1 << 18;
- /** parser, print AST */
- public static final int IS_PRINT_AST = 1 << 19;
- /** parser, print lower AST */
- public static final int IS_PRINT_LOWER_AST = 1 << 20;
- /** parser, print symbols */
- public static final int IS_PRINT_SYMBOLS = 1 << 21;
-
- // callsite tracing, profiling within this function
- /** profile callsites in this function? */
- public static final int IS_PROFILE = 1 << 22;
-
- /** trace callsite enterexit in this function? */
- public static final int IS_TRACE_ENTEREXIT = 1 << 23;
-
- /** trace callsite misses in this function? */
- public static final int IS_TRACE_MISSES = 1 << 24;
-
- /** trace callsite values in this function? */
- public static final int IS_TRACE_VALUES = 1 << 25;
/**
* Whether this function needs the callee {@link ScriptFunction} instance passed to its code as a
* parameter on invocation. Note that we aren't, in fact using this flag in function nodes.
* Rather, it is always calculated (see {@link #needsCallee()}). {@link RecompilableScriptFunctionData}
* will, however, cache the value of this flag.
*/
! public static final int NEEDS_CALLEE = 1 << 26;
/**
* Is the function node cached?
*/
! public static final int IS_CACHED = 1 << 27;
! /** extension callsite flags mask */
! public static final int EXTENSION_CALLSITE_FLAGS = IS_PRINT_PARSE |
! IS_PRINT_LOWER_PARSE | IS_PRINT_AST | IS_PRINT_LOWER_AST |
! IS_PRINT_SYMBOLS | IS_PROFILE | IS_TRACE_ENTEREXIT |
! IS_TRACE_MISSES | IS_TRACE_VALUES;
/** Does this function or any nested functions contain an eval? */
private static final int HAS_DEEP_EVAL = HAS_EVAL | HAS_NESTED_EVAL;
/** Does this function need to store all its variables in scope? */
--- 197,248 ----
public static final int USES_THIS = 1 << 15;
/** Is this declared in a dynamic context */
public static final int IN_DYNAMIC_CONTEXT = 1 << 16;
/**
* Whether this function needs the callee {@link ScriptFunction} instance passed to its code as a
* parameter on invocation. Note that we aren't, in fact using this flag in function nodes.
* Rather, it is always calculated (see {@link #needsCallee()}). {@link RecompilableScriptFunctionData}
* will, however, cache the value of this flag.
*/
! public static final int NEEDS_CALLEE = 1 << 17;
/**
* Is the function node cached?
*/
! public static final int IS_CACHED = 1 << 18;
! /**
! * Does this function contain a super call? (cf. ES6 14.3.5 Static Semantics: HasDirectSuper)
! */
! public static final int ES6_HAS_DIRECT_SUPER = 1 << 19;
!
! /**
! * Does this function use the super binding?
! */
! public static final int ES6_USES_SUPER = 1 << 20;
!
! /**
! * Is this function a (class or object) method?
! */
! public static final int ES6_IS_METHOD = 1 << 21;
!
! /**
! * Is this the constructor method?
! */
! public static final int ES6_IS_CLASS_CONSTRUCTOR = 1 << 22;
!
! /** Is this the constructor of a subclass (i.e., a class with an extends declaration)? */
! public static final int ES6_IS_SUBCLASS_CONSTRUCTOR = 1 << 23;
!
! /** is this a strong mode function? */
! public static final int ES6_IS_STRONG = 1 << 24;
!
! /** Does this function use new.target? */
! public static final int ES6_USES_NEW_TARGET = 1 << 25;
/** Does this function or any nested functions contain an eval? */
private static final int HAS_DEEP_EVAL = HAS_EVAL | HAS_NESTED_EVAL;
/** Does this function need to store all its variables in scope? */
*** 245,256 ****
private static final int MAYBE_NEEDS_ARGUMENTS = USES_ARGUMENTS | HAS_EVAL;
/** Does this function need the parent scope? It needs it if either it or its descendants use variables from it, or have a deep eval, or it's the program. */
public static final int NEEDS_PARENT_SCOPE = USES_ANCESTOR_SCOPE | HAS_DEEP_EVAL | IS_PROGRAM;
/** What is the return type of this function? */
! private Type returnType = Type.UNKNOWN;
/**
* Constructor
*
* @param source the source
--- 252,299 ----
private static final int MAYBE_NEEDS_ARGUMENTS = USES_ARGUMENTS | HAS_EVAL;
/** Does this function need the parent scope? It needs it if either it or its descendants use variables from it, or have a deep eval, or it's the program. */
public static final int NEEDS_PARENT_SCOPE = USES_ANCESTOR_SCOPE | HAS_DEEP_EVAL | IS_PROGRAM;
+
+ /**
+ * The following flags are derived from directive comments within this function.
+ * Note that even IS_STRICT is one such flag but that requires special handling.
+ */
+
+ /** parser, print parse tree */
+ public static final int DEBUG_PRINT_PARSE = 1 << 0;
+ /** parser, print lower parse tree */
+ public static final int DEBUG_PRINT_LOWER_PARSE = 1 << 1;
+ /** parser, print AST */
+ public static final int DEBUG_PRINT_AST = 1 << 2;
+ /** parser, print lower AST */
+ public static final int DEBUG_PRINT_LOWER_AST = 1 << 3;
+ /** parser, print symbols */
+ public static final int DEBUG_PRINT_SYMBOLS = 1 << 4;
+
+ // callsite tracing, profiling within this function
+ /** profile callsites in this function? */
+ public static final int DEBUG_PROFILE = 1 << 5;
+
+ /** trace callsite enterexit in this function? */
+ public static final int DEBUG_TRACE_ENTEREXIT = 1 << 6;
+
+ /** trace callsite misses in this function? */
+ public static final int DEBUG_TRACE_MISSES = 1 << 7;
+
+ /** trace callsite values in this function? */
+ public static final int DEBUG_TRACE_VALUES = 1 << 8;
+
+ /** extension callsite flags mask */
+ public static final int DEBUG_CALLSITE_FLAGS = DEBUG_PRINT_PARSE |
+ DEBUG_PRINT_LOWER_PARSE | DEBUG_PRINT_AST | DEBUG_PRINT_LOWER_AST |
+ DEBUG_PRINT_SYMBOLS | DEBUG_PROFILE | DEBUG_TRACE_ENTEREXIT |
+ DEBUG_TRACE_MISSES | DEBUG_TRACE_VALUES;
+
/** What is the return type of this function? */
! public Type returnType = Type.UNKNOWN;
/**
* Constructor
*
* @param source the source
*** 265,274 ****
--- 308,319 ----
* @param parameters parameter list
* @param kind kind of function as in {@link FunctionNode.Kind}
* @param flags initial flags
* @param body body of the function
* @param endParserState The parser state at the end of the parsing.
+ * @param module the module
+ * @param debugFlags the debug flags
*/
public FunctionNode(
final Source source,
final int lineNumber,
final long token,
*** 280,290 ****
final String name,
final List<IdentNode> parameters,
final FunctionNode.Kind kind,
final int flags,
final Block body,
! final Object endParserState) {
super(token, finish);
this.source = source;
this.lineNumber = lineNumber;
this.ident = ident;
--- 325,337 ----
final String name,
final List<IdentNode> parameters,
final FunctionNode.Kind kind,
final int flags,
final Block body,
! final Object endParserState,
! final Module module,
! final int debugFlags) {
super(token, finish);
this.source = source;
this.lineNumber = lineNumber;
this.ident = ident;
*** 298,307 ****
--- 345,356 ----
this.compileUnit = null;
this.body = body;
this.thisProperties = 0;
this.rootClass = null;
this.endParserState = endParserState;
+ this.module = module;
+ this.debugFlags = debugFlags;
}
private FunctionNode(
final FunctionNode functionNode,
final long lastToken,
*** 333,342 ****
--- 382,393 ----
// the fields below never change - they are final and assigned in constructor
this.ident = functionNode.ident;
this.kind = functionNode.kind;
this.firstToken = functionNode.firstToken;
+ this.module = functionNode.module;
+ this.debugFlags = functionNode.debugFlags;
}
@Override
public Node accept(final LexicalContext lc, final NodeVisitor<? extends LexicalContext> visitor) {
if (visitor.enterFunctionNode(this)) {
*** 364,390 ****
if (getFlag(IS_STRICT)) {
callsiteFlags |= CALLSITE_STRICT;
}
// quick check for extension callsite flags turned on by directives.
! if ((flags & EXTENSION_CALLSITE_FLAGS) == 0) {
return callsiteFlags;
}
! if (getFlag(IS_PROFILE)) {
callsiteFlags |= CALLSITE_PROFILE;
}
! if (getFlag(IS_TRACE_MISSES)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_MISSES;
}
! if (getFlag(IS_TRACE_VALUES)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_ENTEREXIT | CALLSITE_TRACE_VALUES;
}
! if (getFlag(IS_TRACE_ENTEREXIT)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_ENTEREXIT;
}
return callsiteFlags;
}
--- 415,441 ----
if (getFlag(IS_STRICT)) {
callsiteFlags |= CALLSITE_STRICT;
}
// quick check for extension callsite flags turned on by directives.
! if ((debugFlags & DEBUG_CALLSITE_FLAGS) == 0) {
return callsiteFlags;
}
! if (getDebugFlag(DEBUG_PROFILE)) {
callsiteFlags |= CALLSITE_PROFILE;
}
! if (getDebugFlag(DEBUG_TRACE_MISSES)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_MISSES;
}
! if (getDebugFlag(DEBUG_TRACE_VALUES)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_ENTEREXIT | CALLSITE_TRACE_VALUES;
}
! if (getDebugFlag(DEBUG_TRACE_ENTEREXIT)) {
callsiteFlags |= CALLSITE_TRACE | CALLSITE_TRACE_ENTEREXIT;
}
return callsiteFlags;
}
*** 464,490 ****
* @return integer flag for the given directive.
*/
public static int getDirectiveFlag(final String directive) {
switch (directive) {
case "nashorn callsite trace enterexit":
! return IS_TRACE_ENTEREXIT;
case "nashorn callsite trace misses":
! return IS_TRACE_MISSES;
case "nashorn callsite trace objects":
! return IS_TRACE_VALUES;
case "nashorn callsite profile":
! return IS_PROFILE;
case "nashorn print parse":
! return IS_PRINT_PARSE;
case "nashorn print lower parse":
! return IS_PRINT_LOWER_PARSE;
case "nashorn print ast":
! return IS_PRINT_AST;
case "nashorn print lower ast":
! return IS_PRINT_LOWER_AST;
case "nashorn print symbols":
! return IS_PRINT_SYMBOLS;
default:
// unknown/unsupported directive
return 0;
}
}
--- 515,541 ----
* @return integer flag for the given directive.
*/
public static int getDirectiveFlag(final String directive) {
switch (directive) {
case "nashorn callsite trace enterexit":
! return DEBUG_TRACE_ENTEREXIT;
case "nashorn callsite trace misses":
! return DEBUG_TRACE_MISSES;
case "nashorn callsite trace objects":
! return DEBUG_TRACE_VALUES;
case "nashorn callsite profile":
! return DEBUG_PROFILE;
case "nashorn print parse":
! return DEBUG_PRINT_PARSE;
case "nashorn print lower parse":
! return DEBUG_PRINT_LOWER_PARSE;
case "nashorn print ast":
! return DEBUG_PRINT_AST;
case "nashorn print lower ast":
! return DEBUG_PRINT_LOWER_AST;
case "nashorn print symbols":
! return DEBUG_PRINT_SYMBOLS;
default:
// unknown/unsupported directive
return 0;
}
}
*** 577,586 ****
--- 628,656 ----
public FunctionNode setFlag(final LexicalContext lc, final int flag) {
return setFlags(lc, flags | flag);
}
/**
+ * Returns the debug flags for this function.
+ *
+ * @return the debug flags
+ */
+ public int getDebugFlags() {
+ return debugFlags;
+ }
+
+ /**
+ * Checks whether a debug flag is set for this function.
+ *
+ * @param debugFlag the debug flag
+ * @return true if the flag is set
+ */
+ public boolean getDebugFlag(final int debugFlag) {
+ return (debugFlags & debugFlag) != 0;
+ }
+
+ /**
* Returns true if the function is the top-level program.
* @return True if this function node represents the top-level program.
*/
public boolean isProgram() {
return getFlag(IS_PROGRAM);
*** 1063,1072 ****
--- 1133,1222 ----
*/
public FunctionNode setCached(final LexicalContext lc) {
return setFlag(lc, IS_CACHED);
}
+ /**
+ * Checks if the function is generated in strong mode.
+ *
+ * @return true if strong mode enabled for function
+ */
+ public boolean isStrong() {
+ return getFlag(ES6_IS_STRONG);
+ }
+
+ /**
+ * Checks if this is an ES6 method.
+ *
+ * @return true if the ES6 method flag is set
+ */
+ public boolean isMethod() {
+ return getFlag(ES6_IS_METHOD);
+ }
+
+ /**
+ * Checks if this function uses the ES6 super binding.
+ *
+ * @return true if the ES6 super flag is set
+ */
+ public boolean usesSuper() {
+ return getFlag(ES6_USES_SUPER);
+ }
+
+ /**
+ * Checks if this function directly uses the super binding.
+ *
+ * @return true if the ES6 has-direct-super flag is set
+ */
+ public boolean hasDirectSuper() {
+ return getFlag(ES6_HAS_DIRECT_SUPER);
+ }
+
+ /**
+ * Checks if this is an ES6 class constructor.
+ *
+ * @return true if the ES6 class constructor flag is set
+ */
+ public boolean isClassConstructor() {
+ return getFlag(ES6_IS_CLASS_CONSTRUCTOR);
+ }
+
+ /**
+ * Checks if this is an ES6 subclass constructor.
+ *
+ * @return true if the ES6 subclass constructor flag is set
+ */
+ public boolean isSubclassConstructor() {
+ return getFlag(ES6_IS_SUBCLASS_CONSTRUCTOR);
+ }
+
+ /**
+ * Checks if this function uses the ES6 new-targert.
+ *
+ * @return true if the ES6 new-target flag is set
+ */
+ public boolean usesNewTarget() {
+ return getFlag(ES6_USES_NEW_TARGET);
+ }
+
+ /**
+ * Checks if this is an ES6 module.
+ *
+ * @return true if this is an ES6 module
+ */
+ public boolean isModule() {
+ return kind == Kind.MODULE;
+ }
+
+ /**
+ * Returns the functions's ES6 module.
+ *
+ * @return the module, or null if this function is not part of one
+ */
+ public Module getModule() {
+ return module;
+ }
/**
* Get the compile unit used to compile this function
* @see Compiler
* @return the compile unit
< prev index next >