< prev index next >
src/jdk/nashorn/internal/codegen/AssignSymbols.java
Print this page
rev 1338 : 8066222: too strong assertion on function expression names
Reviewed-by: hannesw, lagergren
*** 133,152 ****
}
if (!(functionNode.hasScopeBlock() || functionNode.needsParentScope())) {
functionNode.compilerConstant(SCOPE).setNeedsSlot(false);
}
// Named function expressions that end up not referencing themselves won't need a local slot for the self symbol.
! if(!functionNode.isDeclared() && !functionNode.usesSelfSymbol() && !functionNode.isAnonymous()) {
final Symbol selfSymbol = functionNode.getBody().getExistingSymbol(functionNode.getIdent().getName());
! if(selfSymbol != null) {
! if(selfSymbol.isFunctionSelf()) {
selfSymbol.setNeedsSlot(false);
selfSymbol.clearFlag(Symbol.IS_VAR);
}
- } else {
- assert functionNode.isProgram();
- }
}
return functionNode;
}
private final Deque<Set<String>> thisProperties = new ArrayDeque<>();
--- 133,148 ----
}
if (!(functionNode.hasScopeBlock() || functionNode.needsParentScope())) {
functionNode.compilerConstant(SCOPE).setNeedsSlot(false);
}
// Named function expressions that end up not referencing themselves won't need a local slot for the self symbol.
! if(functionNode.isNamedFunctionExpression() && !functionNode.usesSelfSymbol()) {
final Symbol selfSymbol = functionNode.getBody().getExistingSymbol(functionNode.getIdent().getName());
! if(selfSymbol != null && selfSymbol.isFunctionSelf()) {
selfSymbol.setNeedsSlot(false);
selfSymbol.clearFlag(Symbol.IS_VAR);
}
}
return functionNode;
}
private final Deque<Set<String>> thisProperties = new ArrayDeque<>();
*** 488,513 ****
private void enterFunctionBody() {
final FunctionNode functionNode = lc.getCurrentFunction();
final Block body = lc.getCurrentBlock();
initFunctionWideVariables(functionNode, body);
- if (!functionNode.isProgram() && !functionNode.isDeclared() && !functionNode.isAnonymous()) {
- // It's neither declared nor program - it's a function expression then; assign it a self-symbol unless it's
- // anonymous.
final String name = functionNode.getIdent().getName();
! assert name != null;
! assert body.getExistingSymbol(name) == null;
defineSymbol(body, name, functionNode, IS_VAR | IS_FUNCTION_SELF | HAS_OBJECT_VALUE);
if(functionNode.allVarsInScope()) { // basically, has deep eval
lc.setFlag(functionNode, FunctionNode.USES_SELF_SYMBOL);
}
}
- acceptDeclarations(functionNode, body);
- }
-
@Override
public boolean enterFunctionNode(final FunctionNode functionNode) {
start(functionNode, false);
thisProperties.push(new HashSet<String>());
--- 484,520 ----
private void enterFunctionBody() {
final FunctionNode functionNode = lc.getCurrentFunction();
final Block body = lc.getCurrentBlock();
initFunctionWideVariables(functionNode, body);
+ acceptDeclarations(functionNode, body);
+ defineFunctionSelfSymbol(functionNode, body);
+ }
+
+ private void defineFunctionSelfSymbol(final FunctionNode functionNode, final Block body) {
+ // Function self-symbol is only declared as a local variable for named function expressions. Declared functions
+ // don't need it as they are local variables in their declaring scope.
+ if (!functionNode.isNamedFunctionExpression()) {
+ return;
+ }
final String name = functionNode.getIdent().getName();
! assert name != null; // As it's a named function expression.
!
! if (body.getExistingSymbol(name) != null) {
! // Body already has a declaration for the name. It's either a parameter "function x(x)" or a
! // top-level variable "function x() { ... var x; ... }".
! return;
! }
!
defineSymbol(body, name, functionNode, IS_VAR | IS_FUNCTION_SELF | HAS_OBJECT_VALUE);
if(functionNode.allVarsInScope()) { // basically, has deep eval
+ // We must conservatively presume that eval'd code can dynamically use the function symbol.
lc.setFlag(functionNode, FunctionNode.USES_SELF_SYMBOL);
}
}
@Override
public boolean enterFunctionNode(final FunctionNode functionNode) {
start(functionNode, false);
thisProperties.push(new HashSet<String>());
< prev index next >